Node系列 · Express:断点调试
调试 Node 代码不是只能靠
console.log。Node 自带 Inspector 协议,配合 Chrome DevTools 或 VSCode 就能打断点、单步执行、查看变量——效率提升一个数量级。
一、node --inspect 启动调试模式
node --inspect app.jsDebugger listening on ws://127.0.0.1:9229/xxxxxxx.
For help, see: https://nodejs.org/en/docs/inspectorNode 在 9229 端口开启 WebSocket 调试服务,等待调试客户端连接。
1.1 --inspect-brk 在第一行暂停
node --inspect-brk app.js启动时第一行代码就暂停——适合代码很早就想打断点的情况。
1.2 自定义端口
node --inspect=9222 app.js默认 9229 端口被占用时显式指定。
二、Chrome DevTools 远程调试
node --inspect app.jsChrome 访问 chrome://inspect,会看到:
Remote Target
└── Node.js app.js (file:///path/to/app.js)
inspect点击 inspect → 打开 DevTools → Sources 面板:
- 左侧文件树 → 找到要调试的文件
- 行号左键打断点(红点)
- 代码执行到该行时自动暂停
- 右侧 Scope 看当前作用域的变量
- 顶部按钮:Resume / Step Over / Step Into / Step Out
三、VSCode 调试
VSCode 比 Chrome DevTools 更方便——直接在编辑器里打断点。
3.1 配置 launch.json
.vscode/launch.json:
{
"version": "0.2.0",
"configurations": [
{
"type": "node",
"request": "launch",
"name": "启动并调试",
"program": "${workspaceFolder}/app.js",
"restart": true,
"console": "integratedTerminal"
},
{
"type": "node",
"request": "attach",
"name": "附加到已有进程",
"port": 9229,
"restart": true
}
]
}两种模式:
- Launch:VSCode 启动 Node 进程 + 附加调试器
- Attach:Node 进程已启动(
node --inspect),VSCode 附加上去
3.2 使用
按 F5 启动调试。代码左侧红点 = 断点。
VSCode 调试面板:
| 区域 | 作用 |
|---|---|
| Variables | 当前作用域的所有变量 |
| Watch | 自定义监视表达式(如 user.id) |
| Call Stack | 函数调用栈 |
| Breakpoints | 列出所有断点 |
| Debug Console | 实时执行表达式 |
四、nodemon + --inspect
开发期调试最常见组合——文件改了自动重启 + 断点还在:
nodemon --inspect app.js[nodemon] starting `node --inspect app.js`
Debugger listening on ws://127.0.0.1:9229/xxxx或者在 package.json 里:
{
"scripts": {
"debug": "nodemon --inspect app.js"
}
}npm run debug五、断点类型
5.1 行断点
点击行号左侧——执行到这一行就停。
5.2 条件断点
右键断点 → Edit Breakpoint → 写条件:
// 只有 user.id === 1 时才停
user.id === 15.3 日志断点(不暂停)
右键断点 → Log Message:
用户登录: {user.email}, IP: {req.ip}不暂停执行,只在控制台输出变量值——比 console.log 优雅。
5.4 异常断点
VSCode 调试面板 → Breakpoints 勾选 All Exceptions:
代码抛任何未捕获异常都会暂停在抛出位置——调试最难找的 bug 的利器。
六、单步执行
| 操作 | VSCode 快捷键 | Chrome DevTools | 作用 |
|---|---|---|---|
| 继续 | F5 | Resume | 跑到下一个断点 |
| 单步跳过 | F10 | Step Over | 执行当前行,不进入函数 |
| 单步进入 | F11 | Step Into | 进入函数内部 |
| 单步跳出 | Shift+F11 | Step Out | 跳出当前函数 |
| 重启 | Ctrl+Shift+F5 | - | 重新启动调试 |
| 停止 | Shift+F5 | - | 结束调试 |
七、调试技巧
7.1 Watch 复杂表达式
// 监视:每次暂停时求值
user.orders.length
user.orders.filter(o => o.status === 'paid').length7.2 Debug Console 实时执行
// 在暂停状态下,输入表达式直接看结果
user.id
JSON.stringify(user)
await db.query('SELECT count(*) FROM users')7.3 Source Map
TypeScript / ESM + source map 才能断点到原始代码:
{
"compilerOptions": {
"sourceMap": true
}
}VSCode / Chrome 自动识别 *.map 文件,断点命中到 .ts / .mjs 源文件。
八、生产环境调试
DANGER
永远不要在生产开启 --inspect——它允许任何人连接 9229 端口执行任意代码,等于把服务器控制权交出去。
如需排查生产问题:
| 手段 | 适用 |
|---|---|
| APM(New Relic / Datadog / 阿里云 ARMS) | 性能监控、慢请求分析 |
| 日志聚合(ELK / Loki) | 错误日志检索 |
| OpenTelemetry | 分布式追踪 |
| 错误上报(Sentry) | 异常捕获 + 源码定位 |
九、最佳实践
| 场景 | 推荐 |
|---|---|
| 本地开发 | VSCode + --inspect + 条件断点 |
| 复杂数据流 | Chrome DevTools + Source |
| 异步回调难定位 | VSCode 异常断点(All Exceptions) |
| 项目调试配置 | .vscode/launch.json 提交到仓库 |
| 团队共享 | launch.json 用 ${workspaceFolder} 模板化 |
| 生产 | 永远不开 --inspect;用 APM + 日志 |
十、小结
node --inspect app.js启动 Node Inspector 协议(9229 端口)- Chrome DevTools
chrome://inspect远程调试;VSCode.vscode/launch.json本地调试 - 断点类型:行断点 / 条件断点 / 日志断点 / 异常断点
- 单步:F10 跳过 / F11 进入 / Shift+F11 跳出
- nodemon +
--inspect是开发期调试黄金组合 - 生产不开
--inspect——用 APM / 日志聚合替代
