异步失败时更喜欢抛出或拒绝

时间:2015-05-29 14:23:47

标签: javascript error-handling promise ecmascript-6 bluebird

我有一个包含AJAX请求的Bluebird承诺,需要在请求失败时拒绝承诺。我想提供为什么请求失败的原因,主要是从状态代码中提取到可能附加的任何catch块。为实现这一目标,我有UnauthorizedErrorNotFoundError以及类似的类,所有类都延伸Error以使用Bluebird的模式匹配catch

我不确定的部分是我应该throw还是调用拒绝处理程序。我的代码看起来像:

class Request {
  // other methods

  send(method, url, args, body) {
    return new Promise((res, rej) => {
      let xhr = new XMLHttpRequest();
      xhr.open(method, url);

      xhr.onload = () => {
        res(JSON.parse(xhr.responseText));
      };

      xhr.onerror = () => {
        let status = xhr.status;
        switch (status) {
          case 401:
            // Should I use throw:
            throw new UnauthorizedError(url);
            // or
            rej(new UnauthorizedError(url));
        }
      };

      xhr.send();
    });
  }
}

1 个答案:

答案 0 :(得分:6)

FRONT == (REAR+1)%N构造函数

promise构造函数是安全的,但本质上你通常不会处理内部抛出安全的东西 - 所以例如以下是不安全的:

Promise

promise构造函数通常仅用于将回调API转换为promises,并且因为回调不像是在异步错误(而不是抛出)时必须拒绝的promises。

new Promise(function(resolve, reject){ setTimeout(function(){ // NEVER throw here, it'll throw globally and not reject the promise }, 100); }); 处理程序

两者功能相同。当您从then处理程序中throw时,您将返回被拒绝的承诺。我更喜欢抛出,因为错误比then更明确,但无关紧要。

对于任何承诺实现都是如此,除了Angular 1.x的return区分两者之外 - 但它是奇数球(当你$q时它会记录,即使你处理错误)。

在您的代码中

在您的代码中,您拒绝和处理承诺的方式存在一些错误。 Promise非常强大,因为它们可以为您优雅地处理错误 - 在将回调API转换为承诺时,您必须非常小心:

throw