then(successHandler,failureHandler)的catch()和“错误处理程序”会检测到哪些错误?

时间:2019-04-22 05:13:46

标签: javascript promise

我正在学习Promises,以便在尝试使用Firebase之前可以更好地理解。我是新手,我一直在阅读有关catch()的以下内容:

  • Link one:一篇包含一些练习的文章
  • Link two:SO中的一个问题是为什么我们总是在承诺链之后需要catch()
  • Link three:SO中关于catch()then()的区别的一个问题

从我的阅读中,我得出以下结论:

    在每个Promise链中,必须使用
  • catch(),以防发生“意外异常”。我的failureHandler的{​​{1}}似乎可以检测到这些“意外异常” 。但是,它无法区分“正常故障”与这些类型的故障。我假设那些“意外的异常”之一是在您尝试访问then元素的某些属性时。
  • 似乎我也可以链接null,然后继续执行then(successHandler, failureHandler)块以进行更好的控制,如link two中所述。当我想在某件事失败时执行其他操作(在这种情况下为“正常失败”,而不是“意外异常”),然后将被拒绝的Promise传递给下一个catch()进行处理,因此很有用,这可能很有用如果失败的部分成功,则从结果中得到结果。如果在我的thencatch()内发生故障,我还可以在链的末尾使用successHandler来捕获“意外异常”。

从我的结论可以看出,我对可能发生的错误知之甚少。我提到了failureHandler异常作为“意外异常”的示例之一(这种假设是否正确?)。但是,null还能检测到哪些其他错误,failureHandler还能检测到哪些其他“意外异常”?

我在上面还提到 [catch()]不能区分正常故障与这些类型的故障。那是对的吗?如果是这样,为什么重要呢?

编辑

在阅读了更多内容之后,似乎如果Promise在链的顶部被拒绝,则后面的then会被忽略,我立即进入then块。这就是说,我上面的结论: 当我想在某件事失败并将其他拒绝的Promise传递给下一个catch()处理 时,这很有用。不正确如果是这样的话,如果我在链的末尾已经有一个then,则我的每个catch()块都不再需要failureHandler了。但是,它在链接三中提到:

  

这种说法是,通常您想在   处理,并且您不应该连锁使用它。的   期望您只有一个最终处理程序来处理所有   错误-同时,当您使用“反模式”时,某些   然后不处理回调。

     

但是,此模式实际上非常有用:当您要处理时   正是在此步骤中发生的错误,而您想做   当没有错误发生时-即当   错误是无法恢复的。请注意,这是您的控制分支   流。当然,有时这是需要的。

我的结论是,被拒绝的Promise将传递给下一个then进行处理,因为我阅读了上面的内容。那么 和您想在没有错误发生时(即错误无法恢复时)做完全不同的事情 是什么意思?

1 个答案:

答案 0 :(得分:1)

MDN中我了解到,声明拒绝处理程序的两种方法之间没有真正的区别。

为了成功,很明显,我们将到达实现处理程序:

var promise = new Promise(function(resolve, reject) {
  setTimeout(function() {
    success('success');
  }, 300);
}).then(function(success) {
  console.log(0, success)
}, function(failure) {
  console.log(1, failure)
}).catch(function(failure) {
  console.log(2, failure)
});

对于拒绝,我们将转到第一个拒绝处理程序。
拒绝诺言时:

var promise = new Promise(function(resolve, reject) {
  setTimeout(function() {
    reject('failure');
  }, 300);
}).then(function(success) {
  console.log(0, success)
}, function(failure) {
  console.log(1, failure)
}).catch(function(failure) {
  console.log(2, failure)
});

抛出错误时:

var promise = new Promise(function(resolve, reject) {
  throw "throw";
}).then(function(success) {
  console.log(0, success)
}, function(failure) {
  console.log(1, failure)
}).catch(function(failure) {
  console.log(2, failure)
});

请注意catch块是如何被忽略的,因为它被链接到第一个处理程序的承诺(实现或拒绝)。
如果我们将其更改为拒绝或重新抛出,则将进入catch中的处理程序。

var promise = new Promise(function(resolve, reject) {
  throw "re-throw";
}).then(function(success) {
  console.log(0, success)
}, function(failure) {
  console.log(1, failure)
  throw failure;
}).catch(function(failure) {
  console.log(2, failure)
});

上面链接中的这张图很好地描述了它。 Image from MDN link