首页 > 解决方案 > 等待 Promise.reject 或抛出错误以纾困?

问题描述

我正在将我的承诺链代码重构为异步/等待风格。这样做的原因之一是我想要一个单独的 catch 块来处理所有错误情况(如这里解释的了解 node.js 中的承诺拒绝

我的问题是当我遇到同步错误时,我应该打电话await Promise.reject还是throw error退出这个过程?我知道任何一种方式都行,但我更喜欢throw error。我已经知道我得到了无效的结果,为什么还要等待?使用 throw 立即终止控制流似乎是一个更好的选择。

我不是在谈论承诺链(我的问题的全部意义),所以我不认为线程JavaScript Promises - reject vs. throw回答了我的问题。

我阅读了Node.js 中的错误处理文章,我认为它也没有给出答案。但它确实说

给定的函数应该同步(使用 throw)或异步(使用回调或事件发射器)传递操作错误,但不能同时传递。... 一般来说,使用 throw 并期望调用者使用 try/catch 是非常罕见的......

我的异步函数可能会返回 Promise.reject。因此,我担心引入 2 种方法来传递该文章所针对的错误。

try {
   let result = await aysncFunc().
   if (!isResultValid(result)) { //isResultValid() is sync function 
      await Promise.reject('invalid result')
      //or throw 'invalid result'
   }
   ... //further processing
}
catch (error) {
  ...
}

标签: javascriptnode.jspromiseasync-await

解决方案


在 Promise 控制流中使用它在语义上是正确的throw,这通常是摆脱 Promise 链的更可取的方式。

根据编码风格,await Promise.reject(...)可用于区分实际错误和预期拒绝。带有字符串原因的拒绝承诺是有效的,但throw 'invalid result'被认为是可以用linter 规则解决的样式问题,因为使用Error实例作为异常是常规的。

它之所以重要的原因是因为无法检测到字符串异常instanceof Error并且没有message属性,一致的错误日志记录console.warn(error.message)会导致undefined条目模糊不清。

// ok
class Success extends Error {}
try {
  throw new Success('just a friendly notification');
} catch (err) {
  if (!(err instanceof Success)) {
    console.warn(err.message);
    throw err;
  }
}

// more or less
const SUCCESS = 'just a friendly notification';
try {
  await Promise.reject(SUCCESS);
} catch (err) {
  if (err !== SUCCESS)) {
    console.warn(err.message);
    throw err;
  }
}

// not ok
try {
  throw 'exception';
} catch (err) {
  if (typeof err === 'string') {
    console.warn(err);
  } else {
    console.warn(err.message);
  }

  throw err;
}

由于invalid result实际上是一个错误,因此将其设为一个是合理的:

  throw new TypeError('invalid result');

我不是在谈论承诺链(我的问题的全部要点),所以我不认为线程 JavaScript Promises - reject vs. throw 回答了我的问题。

asyncfunction 是 Promise 链的语法糖,因此适用于 Promise 的所有点也适用async

在某些情况下,抛出错误与拒绝 Promise 不同,但它们特定于其他 Promise 实现,例如 AngularJS $q,并且不会影响 ES6 Promise。构造函数中的同步错误Promise导致异常,这也不适用于async.


推荐阅读