node.js - Promise.all 遭到未处理的拒绝

标签 node.js ecmascript-6 promise es6-promise bluebird

我正在使用 Promise.all 并捕获错误,但仍然收到未处理的拒绝

const Promise = require('bluebird');

function sleep(milis) {
return new Promise(function(resolve, reject) {
    if (milis == 1000) {
        console.log('Rejecting millis', milis)
        setTimeout(() => {
            reject('Got error')
        }, milis);

    } else {
        console.log('Processing millis', milis)
        setTimeout(() => {
            resolve(milis);
        }, milis);

    }
});
}

function test() {

try {
    let lists = [2000, 1000, 3000]
    Promise.all(
            lists.map(record => {
                try {
                    sleep(record)
                } catch (err) {
                    console.log('Error inside catch block1', err)
                    throw err
                }
            })
        ).then(data => {
            console.log('Resolved', data)
        })
        .catch(err => {
            console.log('Error inside catch block2', err)
            throw err

        });

} catch (err) {
    console.log('Error inside catch block3', err)
}
}


test();

使用 catch block 后为什么仍然收到未处理的拒绝。任何帮助表示赞赏。但如果我使用异步等待不会得到未处理的拒绝。

最佳答案

您的代码存在多个问题,让我们逐一解决这些问题:

首先

当您映射 lists 数组时,您永远不会返回从 sleep() 函数获得的 promise 。这意味着您提供给 Promise.all() 的是一个填充有 undefined 的数组。 Promise.all() 将非 Promise 的值视为已解决的 Promise,因此无论 sleep() 创建的 Promise 是解决还是拒绝,您的 Promise.all() 都将始终得到解决。这也意味着没有任何东西可以捕获来自 sleep() 的被拒绝的 Promise,这就是您的脚本当前收到未处理的 Promise 拒绝的原因。 您可以通过使用 return sleep(record) 正确返回 promise 来解决此问题。但这还不足以消除所有未处理的 promise 拒绝,所以让我们继续......

其次

您已将对 sleep() 的调用包装在 try-catch block 中。除非您使用 async-await,否则 try-catch block 将不会捕获被拒绝的 Promise。在这种情况下,它只会捕获创建 Promise 时抛出的错误。如果这是您的意图,那就没问题,但如果您的意图是捕获被拒绝的 promise ,那么它就行不通。

第三

您已将 catch() 处理程序附加到 Promise.all() 中。与前面提到的 try-catch 不同,它实际上会处理任何被拒绝的 promise 。但是,您在此处理程序中重新抛出错误,这意味着 promise 链仍将被拒绝。您已将 Promise.all() 包装在另一个 try-catch block 中,但如上所述,这不会捕获被拒绝的 Promise,因此仍然被拒绝的 Promise 最终将无法处理。
在这种情况下,您不应该在最后一个 catch() 处理程序中重新抛出错误,因为我在这里看不到这样做的任何意义。如果您出于某种原因需要重新抛出它,则需要在链中稍后添加另一个 catch() 处理程序。

关于node.js - Promise.all 遭到未处理的拒绝,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56336280/

相关文章:

javascript - nodeJS require.paths 解决问题

node.js - 如何向除发布者之外的所有订阅者发送消息,发布者也是同一 rabbitMQ 队列上的监听器

javascript - 无法在 Express 中呈现 swig 模板

javascript - 设置实用程序类并在 vue 组件中使用它

javascript - 删除对象成员并且不留下未定义的最佳方法是什么

javascript - .then(functionReference) 和 .then(function(value){return functionReference(value)}) 之间有区别吗?

javascript - 在 Node.js 脚本 for 循环中使用 Promise 时出现问题

node.js - 在node.js中处理ZIP-Buffer

javascript - Visual Studio 中的 EsLint - 无法在 javascript 文件上使用静态属性

javascript - 网络密码 : Promise return Permission denied on Edge