节点和异步/等待,承诺...哪种解决方案最好



使用 Node 并与 Babel 合作,并试图找出 async/await 和 promise 之间的最佳方法。

关键要求:

  • 能够通过我自己的错误
  • 不会导致阻塞
  • 以更ES6/ES7的方式解决问题

我得出了这些:

承诺:

loadByIdPromises: function (req, res, next, _id) {
  console.log('loadByIdc: ', _id);
  Artwork.loadById( { _id } )
    .then( (artwork) => {
      req.artwork = artwork;
      next();
    })
    .catch( (err) => next(new NoDataError('cannot find by ID')));
}

异步/等待:

loadByIdAsync: async function (req, res, next, _id) {
  console.log('loadByIdb: ', _id);
  try {
    req.artwork = await Artwork.loadById( { _id } );
    next();
  } catch (err) {
    next(new NoDataError('cannot find by ID'));
  }
}

或使用包装器异步/等待

let wrap = fn => (...args) => fn(...args).catch(args[2]);
loadByIdAsyncWrap: wrap( async function (req, res, next, _id) {
  console.log('loadByIda: ', _id);
  req.artwork = await Artwork.loadById( { _id } );
  next();
}),

承诺似乎是干净的,但当事情变得复杂时,可能会导致级联。但是有一个漂亮而干净的错误处理。

异步/等待

似乎很干净,但我无法弄清楚如何从等待中抛出错误,而不是整个尝试/捕获。

带有包装器的 Async/Await 似乎很简单,并且(至少在这种情况下 - 节点快速路由器(可以很好地处理错误(但无法设置我自己的错误(。但是包装器特定于req,res,next参数,在我看来,它似乎是外来的东西(就像在我们的css2/3幸福之前html中的额外div(。

选择什么方法?感谢您的建议。

我会使用Promise方法,因为async / await还没有接近主流。

但是,我看到了一个潜在的问题,因为您对next()的调用位于初始块,这意味着您可以成功进行第一阶段,然后调用next(),但是如果出未捕获的错误,调用堆栈将返回一个级别,该错误被您的第一个.catch()块捕获。 然后,即使真正的错误在next()处理程序中,您也会生成该cannot find by ID错误。

相反,我会建议这样做:

function (req, res, next, _id) {
  console.log('loadByIdc: ', _id);
  Artwork.loadById( { _id } )
    .then((artwork) => req.artwork = artwork)
    .then(next, (err) => next(new NoDataError('cannot find by ID')));
}

这仍然会给您留下一个问题,即如何.catch next可能引发的任何异常,但至少您不会被捕获该异常的点误导。

最新更新