快速error handling和asynchronous等待

在我的Node.js应用程序中,我添加了下面的代码来捕获每个未捕获的exception:

process.on('uncaughtException', function (err: Error) { try { logger.err(err); } catch (err) { } }); 

问题是Express有它自己的默认error handling程序,它捕获每个未捕获的exception。 现在,Express在Node(process.on)之前捕获了exception,所以我的logging器没有达到。 但是,可以添加另一个error handling程序,可以在执行Express之前捕获每个exception:

 app.use(logErrors); function logErrors (err: Error, req: Request, res: Response, next: NextFunction) { logger.err(err); next(err); } 

这仍然不包括每一个案件。 每当我有一个async function ,我打电话await ,没有例外,但被拒绝的承诺退还。 例如:

 app.get('/foo', async function (req: Request, res: Response, next: NextFunction) { await bar(); }); function bar() { throw new Exception(); } 

不会达到我的logErrors函数,因为它不会抛出,但会返回一个被拒绝的Promise。

所以要解决它,我用另一个函数包装了我的Express HTTP处理程序:

 app.get('/foo', wrap(async function (req: Request, res: Response, next: NextFunction) { await bar(); })); function wrap(func: (req: Request, res: Response, next: NextFunction) => void) { return async function (req: Request, res: Response, next: NextFunction) { try { await func(req, res, next); } catch (err) { next(err); } } } 

next(err)将错误传递给我的处理程序。 现在,我设法捕捉我的logErrors函数的例外。

我就快完成了。 我仍然有一个我无法理解的错误。 当我调用一个没有await关键字的async function时候,会发生这种情况(在代码的两个不同的地方使用相同的函数有时是有用的,一次是asynchronous调用,一次是同步调用)。 所以这段代码不会出错:

 app.get('/foo', wrap(async function (req: Request, res: Response, next: NextFunction) { bar(); })); 

这里发生的事情是Express HTTP处理程序将parsing的Promise返回给wrap函数。 包装函数反过来,没有达到catch块,所以它不会调用next(err)哪些将达到我的logging器。

bar函数依次返回一个被拒绝的Promise,但是没有人等待它的返回值。

我怎样才能以这样的方式来改变我的代码呢?我不会以任何未经处理的Promise拒绝而结束? (只有通用解决scheme)

还有另一个process.on事件可以为 – unhandledRejection设置一个监听器。

您可以使用它来处理代码中的所有拒绝。

注意 :在logging所有需要的东西之后记得终止你的过程。 更多关于这里 。

我find了一个解决scheme:

 app.get('/foo', async function (req: Request, res: Response, next: NextFunction) { dontAwait(() => bar()); }); async function dontAwait(func: () => void) { try { await func(); } catch (err) { logErrors(err); } } 

我仍然有一个我无法理解的错误。

你可以,但是你现在根本就不会对结果做任何事情。 如果你想要通常的error handling程序触发,你需要 await它。

当我调用一个没有await关键字的async function时,会发生这种情况

我看不出有什么好的理由。 但是,如果你真的想要开火并忘记这个function ,你可以做到。 你只需要明确地处理错误:

 bar().catch(e => logger.err(e));