具有承诺的nodejs控制器的多个存在点

下面的代码片段是一个nodeJS控制器方法,调用一个返回延期承诺的服务。 我试图理解处理多个存在点的最佳方法。

例如,如果服务返回一个空对象,我希望承诺链存在,并向用户返回“Nothing found here”响应。 如果确实find了,则从步骤1进入承诺链中的下一个项目,即步骤2。

从我的testing,似乎是返回的JSON响应,然后下降到下一个逻辑步骤,即第2步。这个逻辑不能在现在的服务处理,即如果没有项目被发现返回一个错误。

module.exports.show = function (req, res) { service.getItem(itemId) .then(function (item) { if (!item) { return res.json('Nothing found here'); } // Step 1 // do some work on the item return item; }) .then(function (foundItem) { // Step 2 // do some more work on the item return res.json('Item has changed ' + foundItem); }) .catch(function (err) { return res.json(err); }); }; 

尝试下面的代码。 该错误被捕获处理程序捕获。 我也改变了if-clause(我认为这就是你的意思):

 module.exports.show = function (req, res) { service.getItem(itemId) .then(function (item) { if (!item) { throw new Error('Nothing found here'); } // Step 1 // do some work on the item return item; }) .then(function (foundItem) { // Step 2 // do some more work on the item return res.json('Item has changed ' + foundItem); }) .catch(function (err) { return res.json(err); }); }; 

记住, then总是返回一个承诺。 如果你自己没有返回一个承诺,一个解决的承诺是自动创build的返回值。

所以, return res.json('Nothing found here')是相同的return Promise.resolve(res.json('Nothing found here')); ,这意味着下一个将会被调用。

如果你不想执行下一步,你只需要拒绝承诺:

 throw new Error('Nothing found here')); // ... .catch(function (err) { return res.json(err.message); }); 

顺便说一句,你可能的意思, if (!item) ,而不是if (item)

 if (!item) { throw new Error('Nothing found here'); } 

如果步骤1和步骤2是同步的,则:

 module.exports.show = function (req, res) { service.getItem(itemId).then(function (item) { if (!item) { throw new Error('Nothing found here'); // this will be caught below } item = doWork_2(doWork_1(item)); // Steps 1 and 2: return res.json('Item has changed ' + item); }).catch(function (err) { return res.json(err.message); }); }; 

doWork_1()doWork_2()都返回已处理的item

如果步骤1和步骤2是asynchronous的,则:

 module.exports.show = function (req, res) { service.getItem(itemId).then(function (item) { if (!item) { throw new Error('Nothing found here'); // this will be caught below } else { return doWork_1(item).then(doWork_2); // Step 1, then Step 2 } }) .then(function (item) { return res.json('Item has changed ' + item); }).catch(function (err) { return res.json(err.message); }); }; 

doWork_1()doWork_2()返回已处理的item解决的承诺。

如果不确定doWork_1().doWork_2()是同步的还是asynchronous的,则使用以下模式来处理这两个事件:

 module.exports.show = function (req, res) { service.getItem(itemId).then(function (item) { if (!item) { throw new Error('Nothing found here'); // this will be caught below } else { return item; } }) .then(doWork_1) // Step 1 .then(doWork_2) // Step 2 .then(function (item) { return res.json('Item has changed ' + item); }).catch(function (err) { return res.json(err.message); }); };