【发布时间】:2025-11-28 00:15:02
【问题描述】:
根据 resolve() 的返回值或传递给 then() 的函数的返回值是否是 Promise,Promise 解析“有帮助”会做不同的事情。
因此,理解和预测行为需要准确地知道正在使用(或允许使用)什么标准来确定某事是否“是一个承诺”,因为我在上面的句子中使用了这个短语,所以我想把它确定下来。我对 Promises/A+ 感兴趣,尤其是 ES6 原生 Promise。
看着https://promisesaplus.com/,它说:
1.1 "promise" is an object or function with a "then" method
whose behavior conforms to this specification.
为了了解这意味着什么,我进一步研究了 2.2 “The then 方法”,发现它依赖于一组 行为标准显然不可能通过算法决定给定对象是否 是不是一个承诺(由停止问题证明)。没关系;它只是意味着规范 有问题的“有用”行为不会直接使用“是一个承诺”这个词。
因此,进一步寻找“有用”行为的规范,我找到了 2.3“承诺解决程序”。 惊喜!它确实直接使用了“是一个承诺”这个词:
2.3.2 If x is a promise, adopt its state [3.4]
但它使自己免于在脚注中陷入无意义:
[3.4] Generally, it will only be known that x is a true promise
if it comes from the current implementation. This clause allows
the use of implementation-specific means to adopt the state of
known-conformant promises.
换句话说,2.3.2 并不是真的意味着“如果 x 是一个承诺”,它真的意味着(并且应该说,IMO)“如果 x 已知是一个承诺”。
但是,如果我理解正确的话,那部分只是一个捷径,它可以证明这样做是安全的。 继续前进,相关部分似乎是 2.3.3,我总结为:将返回值 x 视为承诺 如果 x 有一个名为“then”的属性,它是一个函数。
那么这一切都取决于“x.then 是一个函数”的定义。
确切地说,对于想要实现符合标准的库的人来说,这意味着什么,
或者有人想预测一个符合标准的库在我使用它时必须/可能做什么?
和typeof x.then === "function"一样吗?
希望获得更多线索,我查看了一个所谓符合标准的实现(或一组实现)的规范,ES6 原生承诺, 链接自 MDN 上的 Promises 文档。 我相信相关部分是25.4.1.3.2。 看起来有问题的标准是 IsCallable(x.then);按照链接到那个, 令我沮丧的是 IsCallable 不是一个实际的函数,而是一个“抽象操作”, 用许多其他远非简单的“抽象操作”来定义。
在这一点上,我希望看到任何实现相关决定的符合参考代码的希望似乎正在迅速消退:-(
支持我最初的问题“承诺解决方案如何决定是否将返回值视为承诺?”, 我认为我已经把它归结为更具体的问题,正如我上面解释的:当 Promises/A+ 规范说“是一个函数”时,它到底是什么意思?
如果有一个简单明确的答案(当然这可能会在实现之间留出空间), 立即跟进的问题是:
- 原生 Promise 是否符合简单明确的答案?
- 为什么原生 promises 对 promises/A+ 的“是一个函数”的实现如此复杂?
- 什么是我的合理方式来确保我的返回值将被视为我打算的承诺, 还是按照我的意图作为一个简单的值?
【问题讨论】:
-
'当 Promises/A+ 规范说“是一个函数”时,它到底是什么意思?' - 绝对与 ECMA 规范相同 - “可以作为子例程调用的对象类型的成员”ecma-international.org/ecma-262/6.0/…
标签: javascript promise es6-promise