收集多个承诺结果? (普通的javascript)

时间:2016-10-13 03:09:57

标签: javascript es6-promise

我是Promises的新用户,并尝试首先从localstorage加载大量结果,如果失败,则返回从服务器获取数据。我不想使用jquery - 忽略我目前正在使用$ .getJSON: - /

function loader1() {
    return new Promise(function (resolve, reject) {
        localforage.getItem("data1").then(function (value) {
            if (value !== null) {
                resolve(value);
            } else {
                $.getJSON("/myapp/data1.json").then(function (data) {
                    if (data !== null) {
                        resolve(data);
                    }
                }).catch(function (err) {
                    reject(err);
                });
            }
        });
    });
}

这对一个文件来说很好。那么我就

loader1().then(function(result) { 
    // we have a result
    doSomethingElse();
}).catch(function (err) {
    // problem
});

但我想为多个文件执行此操作,其中一些文件位于localstorage中,其中一些文件从远程源加载json。我想加载所有内容,当它完成后,执行我的应用程序的下一步。

Promise.all似乎是件事,但我无法看到如何获得每个加载器的结果;我以为会是这样的:

Promise
    .all([loader1, loader2, loader3])
    .then(function(result1,result2,result3)) {
        ...

但这不是它的工作方式......所以我试过

Promise
    .all([loader1, loader2, loader3])
    .then(function(result)) {
        // var result1 = result[0];
        // var result2 = result[1];
        // var result3 = result[1];

但第二个结果是函数而不是返回值...

搜索许多网站表明像Q和bluebird这样的承诺系统有spread方法,看起来像我想要的。我可以用普通的旧javascript(如何?)或者我应该使用像Q或RSVP这样的库来实现呢?

3 个答案:

答案 0 :(得分:4)

调用函数

Promise
.all([loader1(), loader2(), loader3()])
.then(function(result) {
  // var result1 = result[0];
  // var result2 = result[1];
  // var result3 = result[1];
 })
 .catch(function (err) {
   // problem
 });

另见How to cache a downloaded javascript fle which is downloaded using script tag

答案 1 :(得分:1)

  

但第二个结果是返回的函数   价值......

您没有解析您构建的Promise的任何值。您也没有从链中的后续.then返回任何值。 您需要为每个加载器函数执行以下操作:

function loader1() {

    var data = localforage.getItem("data1");

    data.then(function (data) {

        if (data !== null) {
             return data;
        } else {
            data = $.getJSON("/myapp/data1.json")

            if (data !== null) {
                return data;
            } else {
                return Error;
        }

    data.catch(function (err) {
       return (err);
    }

这确保了对函数loader1()的调用将返回已解除的Promise og拒绝Promise。然后,您可以使用guest271314建议的解决方案:

Promise
.all([loader1(), loader2(), loader3()])
.then(function(result) {
  // var result1 = result[0];
  // var result2 = result[1];
  // var result3 = result[1];
 })
 .catch(function (err) {
   // problem
 });

但请注意,Promise同步执行 。这意味着它不会自动等待Promise内的任何异步操作完成。只需在异步操作完成后解析它(通常通过解析传递给异步函数的回调),您必须自己处理这个问题。

答案 2 :(得分:0)

您可以使用destructuring

Promise.all([loader1(), loader2(), loader3()])
.then(function([result1, result2, result3]) {
  ...