不像 express 中在末尾處注冊(cè)一個(gè)聲明為 (err, req, res, next) 中間件的方式,koa 剛好相反,在開(kāi)頭進(jìn)行注冊(cè)。
app.use(async (ctx, next) => { try { await next(); } catch (err) { ctx.status = err.status || 500; ctx.body = err.message; ctx.app.emit("error", err, ctx); }});這樣程序中任何報(bào)錯(cuò)都會(huì)收斂到此處。此時(shí)可以方便地將錯(cuò)誤打印到頁(yè)面,開(kāi)發(fā)時(shí)非常便捷。
+ ctx.app.emit('error', err, ctx);koa 也建議通過(guò) app 來(lái)派發(fā)錯(cuò)誤,然后通過(guò)監(jiān)聽(tīng) app 上的 error 事件對(duì)這些錯(cuò)誤做進(jìn)一步的統(tǒng)一處理和集中管理。
app.on("error", (err, ctx) => { /* 錯(cuò)誤的集中處理: * log 出來(lái) * 寫(xiě)入日志 * 寫(xiě)入數(shù)據(jù)庫(kù) * ... */});一個(gè)錯(cuò)誤捕獲并打印到頁(yè)面的示例:
const Koa = require("koa");const app = new Koa();app.use(async (ctx, next) => { try { await next(); } catch (err) { const status = err.status || 500; ctx.status = status; ctx.type = "html"; ctx.body = ` <b>${status}</b> ${err} `; // emmit ctx.app.emit("error", err, ctx); }});app.use(ctx => { const a = "hello"; a = "hello world!"; // TypeError: Assignment to constant variable. ctx.body = a;});app.on("error", (err, ctx) => { console.error("Ooops../n", err);});app.listen(3000);
通過(guò) node server.js 啟動(dòng)后訪問(wèn)頁(yè)面可看到命令行的錯(cuò)誤輸出。
如果使用 pm2,可通過(guò) —no-daemon 參數(shù)使其停留在在命令行以查看輸出。
如果不使用上述參數(shù),可通過(guò) pm2 logs [app-name] 來(lái)查看。
ctx.throw
樸素的拋錯(cuò)方式需要手動(dòng)設(shè)置狀態(tài)碼及信息對(duì)客戶端的可見(jiàn)性。
const err = new Error("err msg");err.status = 401;err.expose = true;throw err;expose 決定是否會(huì)返回錯(cuò)誤詳情給客戶端,否則只展示狀態(tài)對(duì)應(yīng)的錯(cuò)誤文案,比如 500 會(huì)在瀏覽器中展示為 Internal Server Error 。
而通過(guò) ctx.throw 這個(gè) helper 方法會(huì)更加簡(jiǎn)潔。
上面的代碼片段等價(jià)于:
ctx.throw(401, "err msg");
如果不指定狀態(tài)碼,默認(rèn)為 500。5xx 類(lèi)錯(cuò)誤 expose 默認(rèn)為 false ,即不會(huì)將錯(cuò)誤信息返回到 response。
拋錯(cuò)時(shí)還可以傳遞一些額外數(shù)據(jù),這些數(shù)據(jù)會(huì)合并到錯(cuò)誤對(duì)象上,在處理錯(cuò)誤的地方可以從 error 上獲取。
app.use(ctx => { ctx.throw(401, "access_denied", { user: { name: "foo" } });});app.on("error", (err, ctx) => { console.error("Ooops../n", err.user);});參考
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持VeVb武林網(wǎng)。
新聞熱點(diǎn)
疑難解答