【问题标题】:node.js + bluebird: resolving promise.allnode.js + bluebird:解析promise.all
【发布时间】:2017-12-20 00:37:02
【问题描述】:

我有一个函数 requestJSON 查询外部 API 并返回一个(蓝鸟)承诺。

问题: bc 添加到列表之前得到解决,因此promise.all 运行而只有ab 得到解决。

代码:

let promises = [];

// push promise a
promises.push(requestJSON(..));

// push promise b
promises.push(requestJSON(..).then((response) {
  // push promise c
  promises.push(requestJSON({foo: response.bar});
});

promises.all((data) => {
  console.log(data.length) // --> 2
});

问题: 对于这个问题,我想不出一个真正令人满意的解决方案。是否有节点方式/最佳实践?

可能的解决方案

(I) 将 b 包装在另一个 Promise 中,并在 c.then 中解决它。
问题:一个额外的 Promise 除了使代码混乱之外实际上并没有多大作用。 p>

let promises = [];

// push promise a
promises.push(requestJSON(..));

// push helper promise
promises.push(new Promise((resolve, reject) => {
  // push promise b
  promises.push(requestJSON(..).then((response) {
    // push promise c
    promises.push(requestJSON({foo: response.bar});
    // resolve helper promise
    resolve();
  }).catch(..);
}));


promises.all((data) => {
  console.log(data.length) // --> 4
});

(II) 将所有内容放入 b.then
问题:apromise.all 放入 b 中没有语义上的理由 + 该解决方案让我想起了前-promise 回调疯狂。

let promises = [];

// push promise b
promises.push(requestJSON(..).then((response) {
  // push promise a
  promises.push(requestJSON(..));

  // push promise c
  promises.push(requestJSON({foo: response.bar});
  
  promises.all((data) => {
    console.log(data.length) // --> 3
  });
});

【问题讨论】:

    标签: node.js promise bluebird


    【解决方案1】:

    您必须从.then 回调中返回一些内容。如果您想继续等待其他内容,则可以是一个值(然后该承诺被视为已解决)或另一个承诺。

    let promises = [
        requestJSON(/* [1] */),
        requestJSON(/* [2] */).then(response => {
            return requestJSON(/* [3] */);
        })
    ];
    
    // this waits for [1] and [3]
    promises.all(promises).then(results => {
        console.log(data.length);
    });
    

    您的代码没有从.then() 返回任何内容。所以函数返回值为undefined,promise 以undefined 作为结果。

    上面可以写成(注意没有完整的箭头函数中隐含的return):

    let promises = [
        requestJSON(/* [1] */),
        requestJSON(/* [2] */).then(response => requestJSON(/* [3] */))
    ];
    
    promises.all(promises).then(results => console.log(data.length));
    

    【讨论】:

    • 哇,我不知道你可以在里面返回一个你想等待的承诺,谢谢!
    • 是的,您可以构建一个包含任意数量承诺的链,所有承诺一个接一个地解决。使用它的一种方法是var p = dataArray.reduce( (chain, item) => asyncFunction(item), Promise.resolve()); 这将菊花链阵列中的所有项目,以便它们都按顺序处理。从一个空白的 promise Promise.resolve() 开始,返回一个 promise p,当最后一项完成时解析。
    猜你喜欢
    • 2016-11-13
    • 1970-01-01
    • 2015-08-16
    • 1970-01-01
    • 2016-04-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-03-19
    相关资源
    最近更新 更多