本文 AI 產出,尚未審核

Node.js 中的除錯工具

簡介

在 JavaScript 伺服器端開發的過程中,錯誤與除錯往往是最耗時的環節。即使在瀏覽器內已經有成熟的除錯工具,Node.js 仍有自己的挑戰:非同步流程、事件迴圈與外部資源的互動,都可能讓錯誤訊息變得模糊不清。掌握適合的除錯工具,不僅能快速定位問題,還能提升程式碼可維護性與開發效率。

本篇文章針對 Node.js 除錯工具 進行系統性說明,從最簡單的 console 訊息,到完整的 Node InspectorVS Code Debugger、以及第三方的 debug 套件,逐一示範實作方式與注意事項,讓初學者也能在實務專案中得心應手。


核心概念

1. console 系列 – 最基礎的除錯手段

console.logconsole.errorconsole.warnconsole.table 等方法是最直接的除錯方式。雖然簡易,但配合 字串模板顏色標記(如 chalk)可以讓訊息更具可讀性。

// 範例 1:使用 console.log 輸出變數與執行時間
const start = Date.now();
const data = { id: 123, name: 'Alice', age: 28 };
console.log('[INFO] 取得資料:', data);
console.log(`[DEBUG] 執行時間: ${Date.now() - start}ms`);

小技巧:在大型專案中,建議建立自己的 logger 模組,統一格式與等級(info、warn、error)。


2. node --inspect 與 Chrome DevTools

Node.js 從 v6 起內建 V8 Inspector,可以透過 --inspect--inspect-brk 參數啟動遠端除錯,然後使用 Chrome DevTools 連線。

# 範例 2:啟動帶有除錯功能的 Node 程式
node --inspect-brk server.js

啟動後,終端機會顯示類似 ws://127.0.0.1:9229/... 的網址,點擊 Chrome 的 chrome://inspectOpen dedicated DevTools for Node 即可連線。

在 DevTools 中,你可以:

  • 斷點(Breakpoint)
  • 即時檢視變數(Scope / Watch)
  • 執行單步(Step over / Step into)
  • 呼叫堆疊(Call Stack)

提示:若想在程式碼的特定位置自動暫停,只要加入 debugger; 陳述式。

// 範例 3:使用 debugger 陳述式
function calculate(a, b) {
  debugger; // 程式執行到此會自動暫停
  return a + b;
}
calculate(5, 7);

3. VS Code 內建除錯器

Visual Studio Code(以下簡稱 VS Code)提供完整的 Node.js 除錯體驗,無需離開編輯器即可設定斷點、檢視變數、觀察呼叫堆疊。只要在專案根目錄建立 .vscode/launch.json

// 範例 4:VS Code 除錯設定
{
  "version": "0.2.0",
  "configurations": [
    {
      "type": "node",
      "request": "launch",
      "name": "Launch Program",
      "program": "${workspaceFolder}/app.js",
      "runtimeArgs": ["--inspect-brk"],
      "console": "integratedTerminal"
    }
  ]
}

設定完成後,按下 F5(或點擊左側除錯圖示 → 開始除錯)即可進入除錯模式。VS Code 甚至支援 自動重啟nodemon)與 環境變數 的注入。


4. debug 套件 – 讓除錯訊息可切換

debug 是由 TJ Holowaychuk 開發的輕量級除錯工具,透過環境變數 DEBUG 控制訊息顯示,適合在 開發與生產 環境間切換。

# 安裝 debug 套件
npm install debug --save-dev
// 範例 5:使用 debug 套件
const debug = require('debug')('app:server');

function startServer(port) {
  debug('Server is starting on port %d', port);
  // ... 其他程式碼
}

startServer(3000);

執行時只要設定 DEBUG=app:*,即會看到 debug 輸出的訊息;若未設定,則不會有任何輸出,保持 console 清潔。


5. 捕捉未處理的例外與 Promise 錯誤

在 Node.js 中,未捕捉的例外(uncaughtException)與 未處理的 Promise(unhandledRejection)會導致程式直接崩潰。使用 process 事件可以在崩潰前記錄錯誤,並安全關閉服務。

// 範例 6:全域錯誤監聽
process.on('uncaughtException', (err) => {
  console.error('[FATAL] 未捕捉的例外:', err);
  // 最好寫入日誌,然後優雅關閉
  process.exit(1);
});

process.on('unhandledRejection', (reason, promise) => {
  console.warn('[WARN] 未處理的 Promise 拒絕:', reason);
});

注意:即使有上述監聽,仍建議在每個非同步操作內部自行 try/catch.catch(),避免錯誤蔓延。


常見陷阱與最佳實踐

陷阱 可能的後果 解決方案
直接使用 console.log 於大量資料 產生龐大輸出、降低效能,且難以搜尋 使用 log level(如 debugwinston)並限制輸出大小
忘記移除 debugger; 生產環境卡在斷點,服務無法正常運作 於 CI/CD 階段執行 lintno-debugger)檢查
未設定 --inspect-brk 程式在除錯前已執行完畢,無法捕捉早期錯誤 使用 --inspect-brk 讓程式在第一行暫停
只依賴 uncaughtException 可能錯過 Promise 拒絕的錯誤 同時監聽 unhandledRejection
在生產環境開啟 DEBUG=* 大量日誌寫入磁碟,造成 I/O 壓力 僅在 開發或測試 環境開啟,生產使用 log rotation

最佳實踐總結

  1. 統一日誌框架:使用 winstonpinodebug,避免散落的 console.log
  2. 斷點與觀察變數:在非同步回呼或 async/await 區塊前後放置斷點,確保 上下文 正確。
  3. 自動化測試:結合 JestMocha 的錯誤捕捉,提前發現例外。
  4. CI/CD 檢查:加入 ESLint 規則 no-consoleno-debugger,保證程式碼品質。

實際應用場景

場景一:API 伺服器的性能瓶頸

在一個使用 Express 建構的 REST API 中,某個端點回傳速度異常緩慢。使用 node --inspect 連結 Chrome DevTools,於 Event Loop 面板觀察 TimersCPU 使用情況,發現某個資料庫查詢未使用索引,導致阻塞。透過斷點定位到 await db.query(...) 前後的變數,最終優化 SQL,將回應時間從 2.3 秒降至 180ms。

場景二:非同步錯誤導致服務 Crash

一個背景工作(worker)使用 setInterval 定時抓取外部 API。某次外部 API 回傳 500,程式碼只寫了 await fetch(...);,未加 .catch()。結果 unhandledRejection 觸發,服務直接關閉。加入全域 process.on('unhandledRejection') 以及每個 fetch.catch(),不僅避免 Crash,還能把錯誤寫入日誌,方便後續追蹤。

場景三:多開發者協作的除錯流程

團隊使用 VS CodeGitHub Codespaces,每位開發者在本機或遠端容器中執行 npm run dev(內含 --inspect)。除錯設定寫在 .vscode/launch.json,所有人只要按 F5 即可進入除錯模式。透過 Watch 功能觀察 process.env.NODE_ENVreq.body 等關鍵變數,快速定位錯誤來源,提升開發效率。


總結

Node.js 的除錯工具從最簡單的 console 訊息,到功能完整的 V8 InspectorVS Code Debugger,再到可切換的 debug 套件與全域錯誤監聽,每一層都提供了不同的粒度與便利性。掌握這些工具的使用方法,配合 良好的日誌策略斷點技巧全域例外處理,即可在開發階段快速找出問題,並在生產環境保持穩定。

關鍵要點

  • 先從 consoledebugger--inspect → IDE 除錯的層層遞進。
  • 絕不在生產環境直接使用 debugger; 或開啟 DEBUG=*
  • 結合 log framework全域錯誤監聽,建立可觀測、可維護的 Node.js 應用。

透過本文的範例與最佳實踐,你已具備在任何 Node.js 專案中有效除錯的基礎。現在就把這些技巧應用到自己的程式碼裡,讓除錯不再是痛苦的「找錯」過程,而是提升程式品質的 加速器。祝開發順利!