JS Promises:Fulfill vs Resolve

rro*_*and 11 javascript promise

我理解Promise存在于以下三种状态之一:Promise可以是待处理(未解析),履行(成功解决)或拒绝(解决失败).

阅读A + Promise SpecMDN的文档,我很困惑他们都承认已完成被拒绝的状态,但在Promise构造函数的定义中,他们指定了两个回调:resolvereject.我们似乎可以互换地使用这两个术语; 他们不是.

并不意味着成功:

re·solve /r??zälv/ verb
1. settle or find a solution to (a problem, dispute, or contentious matter).
Run Code Online (Sandbox Code Playgroud)

是否意味着成功:

ful·fill /fo?ol?fil/ verb
1. bring to completion or reality; achieve or realize (something desired, promised, or predicted).
2. carry out (a task, duty, or role) as required, pledged, or expected.
Run Code Online (Sandbox Code Playgroud)

当我们真正实现承诺时,为什么我们在这里使用决心?有没有在其中的价值,我们通过一个实例解决可能会导致无极是拒绝 ED?

jib*_*jib 9

我们可以用另一个承诺来解决一个承诺。

首先回答你的第二个问题:是的,有一个例子,我们传递给 resolve 的值可能会导致 Promise 被拒绝,那就是如果我们传递一个被拒绝的承诺,例如Promise.reject()

回答你的第一个问题不是解决实现相同:考虑我们传递给解决的值是一个未决承诺的情况。在这种情况下,我们自己的承诺不会立即解决

a().then(() => new Promise(setTimeout)).catch(e => console.error(e));
Run Code Online (Sandbox Code Playgroud)

在这种情况下,我们说一个 promise 被“解析为”另一个 promise,并且它保持未决状态。

这一切都发生在我们背后的 inside 中then,因此查看a不支持承诺(需要回调)的老式案例可能更容易,并且我们没有正确地展平事物:

// Old times and unflattened for exposition:
new Promise((resolve, reject) => a(function(result) {
  resolve(new Promise(setTimeout));
}, reject))
.then(() => console.log("after setTimeout"))
.catch(e => console.error(e));
Run Code Online (Sandbox Code Playgroud)

在这里我们更清楚地看到,resolve是用另一个 promise 调用的。重要的是,已解决的承诺不会履行并触发"after setTimeout"消息,直到第二个承诺解决(具有来自 的非承诺undefinedsetTimeout),此时两个承诺都已履行(换句话说:这两个承诺只是形成了一个解决链)。

这是理解已解决与已完成甚至已解决(已完成或已拒绝,而非未决)不同的关键。

来自国家和命运

  • 状态:已完成、已拒绝未决
  • 命运:已解决未解决

命运是指单承诺的命运是否已经达成,并不直接对应,因为决心链的任何状态转变。


tri*_*cot 9

事实上,resolve回调并不意味着承诺会被履行

该条款履行,拒绝,待批入驻,解决锁定在中定义EcmaScript2015规格,25.4无极对象

任何 Promise 对象都处于以下三种互斥状态之一:满足拒绝挂起

  • p如果p.then(f, r)将立即排队 Job 以调用该函数,则承诺已实现f

  • 如果承诺立即将 Job 排队以调用该函数,p则该承诺将被拒绝。p.then(f, r)r

  • 如果一个 promise 既没有被实现也没有被拒绝,那么它就是待处理的。

一诺被认为是解决如果没有挂起,如果它要么履行或拒绝,即。

如果一个承诺被解决或者它被“锁定”以匹配另一个承诺的状态,那么它就会被解决。尝试解决或拒绝已解决的承诺没有效果。如果一个 promise没有解决,它就是未解决的。未解决的承诺始终处于挂起状态。已解决的承诺可能是未决的、已完成的或被拒绝的。

一个简短的概述,我将使用术语“自主”作为“锁定”的反义词。它们是 promise 依赖情况的两个可能值:

行动 依赖 状态 解决? 安定了吗?
new Promise((resolve, reject) => ...) 自主性 待办的
...resolve(thenable) 锁定 待办的* 是的
...resolve(other) 自主性 完成 是的 是的
...reject(any) 自主性 拒绝了 是的 是的

* thenable 现在可以控制我们的 promise 对象的未来状态。

上面的引用提到一个承诺被锁定以匹配“另一个承诺”的状态,但更准确地说,“另一个承诺”也可以是一个非承诺的“thenable”,如步骤 11 和 12 所示25.4.1.3.2中的过程描述

  1. 如果 IsCallable( thenAction ) 是false,则
          a. 返回 FulfillPromise( promise,resolution )。
  2. 执行 EnqueueJob ( "PromiseJobs", PromiseResolveThenableJob, «?promise, resolution, thenAction» )

的演示resolve被称为具有thenable,这反过来又触发拒绝:

const thenable = { // Could be a promise object, but does not have to be
    then(success, fail) {
        setTimeout(() => fail("gotcha!"), 1000);
    }
}

const p = new Promise((resolve, reject) => {
    console.log("1. The promise is created as pending");
    setTimeout(() => {
        resolve(thenable);
        console.log("2. It's resolved with a thenable; it's not yet settled");
    }, 1000);
});

p.catch(err => 
   console.log(`3. It's settled as rejected with error message "${err}"`)
);
Run Code Online (Sandbox Code Playgroud)