先运行lsof -iTCP -sTCP:LISTEN -n -P | grep :端口号查真占用,无输出则说明端口空闲、问题在Dart扩展自动恢复机制;解决方式是在.vscode/settings.json中设"dart.vmServicePort": 51234并重启VSCode。

怎么判断 Dart VM 服务端口是不是真被占了
VSCode 启动 Flutter 调试时卡在 “Waiting for connection” 或报 Address already in use,别急着 kill -9。Dart VM 服务(比如 50321、5000)的“占用”常是假象:它可能只是上一个调试会话崩溃后没释放句柄,或 VSCode 的 Dart 扩展在后台悄悄复用了端口。
先验证是不是真冲突:
- 运行
lsof -iTCP -sTCP:LISTEN -n -P | grep :50321(把50321换成你实际报错的端口),看输出里是否有dart或flutter_tools进程;没有就说明端口空闲,问题在扩展生命周期管理 - 如果输出显示
-或空白进程名,加-iTCP和-n参数避免 DNS 解析干扰,否则容易漏判 - 再查一次
ps aux | grep -E "(dart|flutter_tools)",确认有没有残留子进程——有时候lsof不显示,但ps能揪出dart主进程下挂着的 VM 子线程
为什么 kill 掉进程后端口立刻又被占
这不是系统级端口复用,而是 Dart/Flutter 扩展的“自动恢复”机制在作祟。VSCode 的 Dart 插件默认启用后台分析服务(Analysis Server)和调试代理(Debug Adapter),它们会监听固定端口,并在检测到异常终止后几秒内自动重启监听。
典型表现:
- 你刚
kill -9掉 PID,2 秒后lsof又看到同一端口被dart占着,且 PID 变了 - VSCode 状态栏右下角显示 “Dart Analyzer starting…” 或反复闪动 “Connecting to VM Service”
- 关闭所有编辑器窗口、甚至退出 VSCode,再重开,端口还是被占——说明扩展在全局工作区级缓存了监听状态
如何让 Dart VM 端口自动换一个而不是硬杀
最稳的办法不是对抗冲突,而是绕过它。Dart SDK 支持通过环境变量指定 VM 服务端口,VSCode 的 Dart 扩展会尊重这个设置,且不与分析服务冲突。
操作步骤:
- 在项目根目录下新建
.vscode/settings.json,写入:{"dart.vmServicePort": 50322} - 或者更彻底:在终端启动 VSCode 前设环境变量
export DART_VM_SERVICE_PORT=50322,再运行code . - 注意不要改
dart.flutterSdkPath或其他 SDK 路径配置,只动这个端口字段;改完必须重启 VSCode,旧调试会话不会 reload 配置 - 如果用的是跨端调试(
type: "cross-platform"),确保launch.json里没硬编码vmServicePort字段,否则会覆盖设置
哪些端口不能随便改,改了反而更麻烦
Dart VM 服务端口不是随便填个数字就行。某些范围会被系统或网络策略拦截,或与 Flutter 工具链内部逻辑冲突。
避坑要点:
- 避开
0–1023:需要 root 权限,VSCode 普通用户启动会失败 - 避开
5000–5100:Flutter 工具默认扫描这个区间找可用端口,填这里可能触发重复探测逻辑,导致“端口刚换又撞上” - 避开
8000–8100:很多本地开发服务(如 Webpack Dev Server、Vite)默认占这个段,容易二次冲突 - 推荐填
50300–50400以外的四位数,比如51234或59876,既避开默认扫描区,又足够高不易被其他工具抢占
端口本身不重要,重要的是让 Dart 扩展放弃“抢默认端口”的执念——它一旦开始用你指定的端口,就不会再试图复用旧端口或触发自动恢复逻辑。


















