如果你用另一个承诺解决一个承诺会发生什么

What should happen if you resolve a promise with another promise?

本文关键字:一个承诺 什么 解决 如果      更新时间:2023-09-26

ECMAScript 6.0 规范对解析另一个Promise Promise有什么看法?它是否应该通过附加一个then来解决这个问题Promise来采用其他Promise的状态?

我在Chrome中尝试了这个片段,这就是我得到的,它似乎只是解决了Promise1 Promise2可以吗?

> Promise1 = new Promise(function(resolve){ResolveYouLater1 = resolve})
> Promise2 = new Promise(function(resolve){ResolveYouLater2 = resolve})
> ResolveYouLater1(Promise2)
  undefined
> Promise1
  Promise {[[PromiseStatus]]: "resolved", [[PromiseValue]]: Promise}

我认为它应该在 Promise2 上附加一个then,当Promise2已解决时应该ResolveYouLater1(value)

ECMAScript 6.0 规范对一个承诺解析另一个承诺有什么看法?

您可以在此处自己阅读:http://www.ecma-international.org/ecma-262/6.0/#sec-promise-resolve-functions
当参数是 thenable 时,PromiseResolveThenableJob 将被排队。

它是否应该采用另一个承诺的状态,在该承诺上附加一个可以解决这个问题的承诺?

是的。.then()方法将使用解析器和拒绝器函数调用。

我在 Chrome 中尝试了这个片段,这就是我得到的,它似乎只是用 Promise1 解决 Promise2 好吗?

是的。它只是暂时解决。


不得不承认,我当前的Chrome版本(48.0.2564.82,V8 4.8.271.17)并不完全符合此算法(这本身可能不是一件坏事,并避免了内存问题,但可能是意想不到的)。
它是惰性的,并且仅在实际回调对结果感兴趣时才调度作业。它不会将解析器传递给 then 方法,而是将想知道结果的实际回调传递给方法。

> var resolve1, resolve2;
> var promise1 = new Promise(function(r){ resolve1 = r; });
> var promise2 = new Promise(function(r){ resolve2 = r; });
> promise2.then = function(...args) { console.log(...args);
>                                     return Promise.prototype.then.call(this, ...args); };
> resolve1(promise2);
  undefined
// you'd expected a call to the then method here
> promise1
  Promise {[[PromiseStatus]]: "resolved", [[PromiseValue]]: Promise}
> promise2
  Promise {[[PromiseStatus]]: "pending", [[PromiseValue]]: undefined}
> resolve2(42)
  undefined
// or at least here
> promise1
  Promise {[[PromiseStatus]]: "resolved", [[PromiseValue]]: Promise}
> promise2
  Promise {[[PromiseStatus]]: "resolved", [[PromiseValue]]: 42}
> promise1.then(x => console.log(x))
  x => console.log(x), PromiseIdRejectHandler() { [native code] }
  // but it only is here
  42
  Promise {[[PromiseStatus]]: "pending", [[PromiseValue]]: undefined}
> promise2.then(x => console.log(x))
  x => console.log(x)
  42
  Promise {[[PromiseStatus]]: "pending", [[PromiseValue]]: undefined}
> promise1.then(x => console.log(x))
  x => console.log(x), PromiseIdRejectHandler() { [native code] }
// hell they're even calling it multiple times!
42
Promise {[[PromiseStatus]]: "pending", [[PromiseValue]]: undefined}

> var resolve1, resolve2;
> var promise1 = new Promise(function(r){ resolve1 = r; });
> var thenable = {then:function(r) { console.log(...arguments); resolve2 = r; }};
> resolve1(thenable);
  undefined
// you'd expected a call to the then method here
> promise1
  Promise {[[PromiseStatus]]: "resolved", [[PromiseValue]]: Object}
> thenable
  Object {}
> resolve2(42)
  Uncaught TypeError: resolve2 is not a function(…)
// uh. yeah.
> promise1.then(x => console.log(x))
  () { [native code] }, () { [native code] }
// ah there was the call, even with a resolver
  Promise {[[PromiseStatus]]: "pending", [[PromiseValue]]: undefined}
> resolve2(42)
  42
  undefined
> promise1.then(x => console.log(x))
  () { [native code] }, () { [native code] }
// but now they fucked up.
// Instead of another call on the thenable, you'd expected the result to be logged
  Promise {[[PromiseStatus]]: "pending", [[PromiseValue]]: undefined}
> resolve2(42)
  42
// OMG.
  undefined