如何将拒绝的承诺转换为异常并将其从Express路由处理程序中抛出?

时间:2015-08-06 07:02:57

标签: javascript node.js express promise q

在我的应用程序的一个路由处理程序中,我正在调用一个返回Q promise的方法。我没有使用.catch方法处理拒绝,而是希望它被抛出并被我的Express应用程序的catch-all错误处理程序捕获。

我尝试了Q的done方法,但它异步抛出异常,因此它不是由我的catch-all错误处理程序处理,而是一直传播并且我的应用程序被终止:

// The route handler 

function index(req, res) {
    dao.findById(id).then(function (data) {
        res.send(data);
    }).done();
}

// The catch all event-handler

function catchAllErrorHandler(err, req, res, next) {
    console.log(err, req, res);
}

// Registration of the catch-all event handler

app.use(catchAllErrorHandler);

错误永远不会进入catch all错误处理程序。有没有办法让抛出的错误由catchAllErrorHandler处理?

2 个答案:

答案 0 :(得分:4)

这不会直接回答您的问题,而是显示实现目标的另一种方式。

express中的每个中间件处理程序都具有签名(request, response, next)。目前,您的index功能没有下一个定义。

当使用参数调用next时,express会将该参数视为错误,并对其进行适当管理。

因此,在您的情况下,更改您的index函数以包含下一个参数,并将.done()更改为.catch(next),这将调用下一个发生的任何错误,并允许表达处理它。

dao.findById(id)
   // Handle success
    .then(function (data) {
        res.send(data);
    })
    // Handle failure
    .catch(next);

答案 1 :(得分:2)

  

我尝试了Q的完成方法

这可能是你从承诺中抛出异常的最好方法。

  

但它异步抛出异常

当然,承诺始终是异步的。您无法确定您的承诺将来是否会拒绝并同步抛出异常......

  

有没有办法让catchAllErrorHandler处理抛出的错误?

将处理程序显式地作为处理程序传递:

dao.findById(id).then(function (data) {
    res.send(data);
}).catch(catchAllErrorHandler);

或者,从Q v1.3起,您可以使用unhandled rejection tracking并将catchAllErrorHandler放在那里。