Javascript 理解。然后()ES6

Javascript 理解。然后()ES6,javascript,asynchronous,promise,es6-promise,Javascript,Asynchronous,Promise,Es6 Promise,我在代码中遇到了一个让我困惑了很长时间的错误,我正在寻找一些澄清 在这段代码中,注释掉的内部承诺导致了一个问题。最后的Promise.all()会在setTimeout命中时继续,而不是在超时内的解析之后 用承诺包装异步代码可以解决流问题,但这是为什么呢 本质上,为什么我们不能在.then()链中运行普通异步代码,在异步回调的末尾返回一个Promise.resolve() var asyncPromise = function() { return new Promise(functio

我在代码中遇到了一个让我困惑了很长时间的错误,我正在寻找一些澄清

在这段代码中,注释掉的内部承诺导致了一个问题。最后的Promise.all()会在setTimeout命中时继续,而不是在超时内的解析之后

用承诺包装异步代码可以解决流问题,但这是为什么呢

本质上,为什么我们不能在.then()链中运行普通异步代码,在异步回调的末尾返回一个Promise.resolve()

var asyncPromise = function() {
    return new Promise(function(resolve, reject) {
        setTimeout(function() {
            console.log('Async Promise done');
            resolve();
        }, 1000);
    });
};

var generateSignupPromises = function(qty) {
    var promiseArray = [];
    for (var i = 1; i <= qty; i++) {
        promiseArray.push(
            function() {
                return asyncPromise()
                .then(function() {
                    console.log('Before Timeout');

                  //Uncommenting this fixes the issue
                  //return new Promise(function(resolve, reject) {
                        setTimeout(function() {
                            console.log('After Timeout');
                            //resolve();
                            return Promise.resolve();
                        }, 500);
                  //})
                });
            }
        );
    }
    return promiseArray;
};

var test = generateSignupPromises(1);

Promise.all([test[0]()])
.then(function() {
    console.log('Done');
});
var asyncPromise=function(){
返回新承诺(功能(解决、拒绝){
setTimeout(函数(){
log('Async Promise done');
解决();
}, 1000);
});
};
var generateSignupPromises=功能(数量){
var promiseArray=[];

for(var i=1;i是一个同步函数,所以如果您想在其中执行异步任务,那么必须返回一个承诺

另外,Promise.all需要一个承诺数组,而不是数组数组数组

var asyncPromise = function() {
  return new Promise(function(resolve, reject) {
    setTimeout(function() {
      console.log('Async Promise done');
      resolve();
    }, 1000);
  });
};

var generateSignupPromises = function(qty) {
  var promiseArray = [];
  for (var i = 1; i <= qty; i++) {
    promiseArray.push(
      function() {
        return asyncPromise()
        .then(function() {
          console.log('Before Timeout');

          //Uncommenting this fixes the issue
          return new Promise(function(resolve, reject) {
          setTimeout(function() {
            console.log('After Timeout');
            resolve();
            //return Promise.resolve();
          }, 500);
          })
        });
      }
    );
  }
  return promiseArray;
};

var test = generateSignupPromises(1);

Promise.all([test[0]()])
.then(function() {
  console.log('Done');
});
var asyncPromise=function(){
返回新承诺(功能(解决、拒绝){
setTimeout(函数(){
log('Async Promise done');
解决();
}, 1000);
});
};
var generateSignupPromises=功能(数量){
var promiseArray=[];
对于(var i=1;i
为什么我们不能在.then()链中运行普通的异步代码,在异步回调的末尾返回一个Promise.resolve()

var asyncPromise = function() {
    return new Promise(function(resolve, reject) {
        setTimeout(function() {
            console.log('Async Promise done');
            resolve();
        }, 1000);
    });
};

var generateSignupPromises = function(qty) {
    var promiseArray = [];
    for (var i = 1; i <= qty; i++) {
        promiseArray.push(
            function() {
                return asyncPromise()
                .then(function() {
                    console.log('Before Timeout');

                  //Uncommenting this fixes the issue
                  //return new Promise(function(resolve, reject) {
                        setTimeout(function() {
                            console.log('After Timeout');
                            //resolve();
                            return Promise.resolve();
                        }, 500);
                  //})
                });
            }
        );
    }
    return promiseArray;
};

var test = generateSignupPromises(1);

Promise.all([test[0]()])
.then(function() {
    console.log('Done');
});
您完全可以。但是任何值——无论是承诺还是其他什么——从普通异步回调返回的
都会像往常一样被忽略

then
回调中启动异步操作不会改变这一点,
setTimeout
不会返回承诺,
then
也不会知道它可以等待的任何异步事件

如果您希望从回调返回一个承诺,并获得该最终结果的另一个承诺,那么它必须是
然后
回调:

asyncPromise()
.then(function() {
    return new Promise(function(resolve, reject) {
//  ^^^^^^
        setTimeout(resolve, 500);
    }).then(function() {
//     ^^^^^^^^^^^^^^^
        return Promise.resolve();
    });
});

我真的不知道你想做什么,但是
setTimeout()中的
返回
处理程序几乎没有什么意义;没有任何东西会注意返回值。末日金字塔+大量匿名函数=不可读代码+意外行为。setTimeout不是异步的。它同步返回,导致您的then()返回未定义的“承诺”结尾。通过添加额外的行,它将返回另一个承诺,该承诺将等待
resolve
。顺便说一句,这不是应该使用承诺的方式。