Node.js Express unhandledRejection removeListener

时间:2016-11-22 17:21:31

标签: node.js express

我的Express应用程序中有一些错误处理,用于异步/等待功能,即。试图集中处理未被捕获的错误,以适当的状态代码/消息进行响应。

我这样做:

const handleRejection = (res, reason) => {
    const { code, message } = reason
    console.trace()
    logger.error(reason)
    // use `res` to send response to client
}

app.use((req, res, next) => {
    process.on('unhandledRejection', handleRejection.bind(this, res))
    next()
})

process.on('SIGTERM', () => process.removeListener('unhandledRejection', handleRejection))

这适用于捕获/处理错误,但是,每次触发错误时,我的日志都会被填满。我不相信这个事件监听器process.on('unhandledRejection')正在被正确删除......

有解决方法吗?

2 个答案:

答案 0 :(得分:2)

您似乎在每次请求时附加了一个新的事件处理程序。

然后,在SIGTERM上,您尝试删除从未附加的事件处理程序handleRejection - 您没有附加handleRejectionhandleRejection.bind(this, res)会返回不同的函数。

看起来你也可能通过将函数绑定到每个请求的每个res对象来泄漏内存。

这是处理错误的一种非常奇怪的方法。我甚至不确定这确实是你想要做的。当你试图退出服务器时,是否要添加这么多事件hendler(每个请求对服务器发出一个请求)然后在SIGTERM上删除所有这些事件?

答案 1 :(得分:0)

这是我的Express中间件解决方案,将unhandledRejection传递给主错误中间件

    // Handle unhandledRejection and pass error to next middleware
    app.use(function (req, res, next) {

        function unhandledRejection(reason, p) {
            console.error('Possibly Unhandled Rejection at: Promise ', p, " reason: ", reason);

            next(reason);
        }

        process.on('unhandledRejection', unhandledRejection);

        // Manage to get information from the response too, just like Connect.logger does:
        var end = res.end;
        res.end = function (chunk, encoding) {

            // Prevent MaxListener on process.events
            process.removeListener('unhandledRejection', unhandledRejection);
            res.end = end;
            res.end(chunk, encoding);
        };
        next();
    });