Javascript 捕获异步等待快速路由处理程序中的所有错误
假设我有这样一条路线:Javascript 捕获异步等待快速路由处理程序中的所有错误,javascript,express,async-await,Javascript,Express,Async Await,假设我有这样一条路线: app.get('/broken', (req, res) => { throw new Error('Broken!'); }); 这将永远不会向客户端发送响应 但是,我可以为所有错误添加中间件: const errorMiddleware = (error, req, res, next) => { if (error) { console.error(error); return res.status(500) .j
app.get('/broken', (req, res) => {
throw new Error('Broken!');
});
这将永远不会向客户端发送响应
但是,我可以为所有错误添加中间件:
const errorMiddleware = (error, req, res, next) => {
if (error) {
console.error(error);
return res.status(500)
.json({
message: 'Internal server error',
});
}
next(error);
};
但这对异步
路由不起作用,因为它们不直接抛出
例如,这将不起作用:
app.get('/broken', async (req, res) => {
throw new Error('Broken!');
});
因此,我可以创建如下包装:
const asyncRoute = f => (req, res, next) => {
return Promise.resolve(f(req, res, next)).catch(next);
};
app.get('/broken', asyncRoute(async (req, res) => {
throw new Error('Broken!');
}));
但这真的很痛苦,因为现在我必须为每条路线调用这个函数
什么是更好的处理方法
- 答案正是我上面描述的
- 对的回答不使用
wait
异步
函数传递到Express的app.get
,因为app.get
不处理函数返回的承诺。因此,您需要包装这些async
处理程序(正如您所做的那样)
通过在模块顶部为自己提供一个实用方法,您可以避免每次都这样做:
const appGet = handler => app.get(asyncRoute(handler));
然后使用它而不是应用程序。获取:
appGet('/broken', async (req, res) => {
throw new Error('Broken!');
});
在某个时候(可能不是现在),您可能想看看。您认为使路由回调异步
有什么好处?Express没有使用承诺,所以。。。它纯粹是为了在它里面获得wait
语义吗?如果是这样的话,那么你的包装器就是实现这一点的正确方法。(你可能会看到。)我的一些路由需要多个async
调用(例如数据库、API、bcrypt),因此在async
上下文中更容易编写。@T.J.Crowder如果我没有通过一个承诺(例如123
),那么我希望强制承诺(例如,Promise.resolve(123)
)。请注意,Promise.resolve(Promise.resolve(x))
被展平为Promise.resolve(x)
。好的。我不认为有任何理由将非承诺传递到名为asynchroute
的东西中,所以我没有意识到您想要处理它。:-)