跳至主要内容

Node.js Error Handling

📌 1. 錯誤分類

錯誤類型範例是否可捕捉
語法錯誤 (SyntaxError)JSON.parse('[')否,執行前報錯
執行期錯誤 (RuntimeError)foo.bar()✅ 可使用 try-catch
非同步錯誤 (Async error)fs.readFile() callback✅ 需在 callback 或 catch 處理
未捕捉例外無 try-catch 包裹❌ 會導致 process crash
未處理 Promise 拋錯Promise 未加 .catch()❌ 會觸發全域錯誤

📌 2. 同步錯誤處理(try-catch)

try {
const json = JSON.parse('{ invalid }');
} catch (err) {
console.error('解析錯誤:', err.message);
}

✅ try-catch 僅限於同步執行區塊。

📌 3. 非同步錯誤處理(callback / async)

callback 範例:

fs.readFile('notfound.txt', (err, data) => {
if (err) {
console.error('讀檔錯誤:', err.message);
return;
}
console.log(data);
});

async/await 錯誤捕捉:

async function loadFile() {
try {
const data = await fs.promises.readFile('test.txt');
console.log(data.toString());
} catch (err) {
console.error('讀檔錯誤:', err.message);
}
}

📌 4. Promise 錯誤處理

doSomething()
.then(result => doNext(result))
.catch(err => {
console.error('錯誤發生:', err.message);
});

✅ 所有鏈式 Promise 中只需一個 .catch() 處理整體錯誤。

📌 5. 全域錯誤監控

事件用途
process.on('uncaughtException')捕捉未處理的同步錯誤(不建議繼續執行)
process.on('unhandledRejection')捕捉未處理的 Promise 拋錯
process.on('uncaughtException', err => {
console.error('未捕捉例外:', err);
process.exit(1); // 建議退出,避免應用進入不穩定狀態
});

process.on('unhandledRejection', reason => {
console.error('未處理 Promise 拋錯:', reason);
});

📌 6. 實務建議

作法建議
所有 async function 加 try-catch✅ 必要
中央錯誤處理 middleware(如 Express)✅ 集中處理
不依賴 uncaughtException 作業務處理❌ 不建議
拋出 Error 實體(非字串)✅ throw new Error('訊息')
使用型別區分錯誤類型(自訂 error class)✅ 增強可讀性與可維護性

📌 7. 常見面試題與解析

🧠 Q1:try-catch 可以包住 fs.readFile() 嗎?

✅ 建議答法:

不行,因為 fs.readFile() 是非同步函式。錯誤只能在 callback 中處理,或使用 fs.promises.readFile() 搭配 async/await 包在 try-catch 裡處理。


🧠 Q2:為何不建議依賴 uncaughtException 處理錯誤後繼續執行?

✅ 建議答法:

uncaughtException 可能發生在程式進入非預期狀態,無法保證系統完整性與安全性,因此只應記錄錯誤後優雅關閉服務。


🧠 Q3:如何設計可重用的錯誤處理機制?

✅ 建議:

  • 建立自訂錯誤類別(如 AppError, ValidationError)
  • 在中介層統一包裝錯誤
  • 中央錯誤處理器統一處理輸出格式與狀態碼

📘 延伸學習資源