为使用者提供可靠的、可协做的JavaScript Promises的一个开放标准javascript
一个promise表示一个异步操做的最终结果。和一个promise交互的主要方式是经过注册了回调函数的then
方法,其中回调函数可以获取promise最终的值或者该promise没法执行的缘由。java
此规范详述了提供了then
方法的行为,全部遵循Promises/A+规范的promise实现都可将本标准做为参照基础来实施then
方法。所以此规范必须十分稳定。尽管Promises/A+组织可能偶尔作向后兼容的小小改变来修改这一规范,从而解决新发现的边界状况,咱们只在谨慎地考虑、讨论和测试后,整合一些大的或是不向后兼容的变化。git
从历史上看,Promises/A+阐明了更早的Promises/A建议的行为条例,将其扩展为包含实际上存在的行为,而且删减了在特殊状况下和有问题的部分。github
最后,核心的Promises/A+规范不涉及处理如何建立,执行或是拒绝promise,而是选择聚焦于提供一个可协做的then
方法。将来的其余规范可能会涉及到这些方面。算法
1.1. “promise”是一个具备then
方法的对象或函数,其中then
方法遵循此规范。promise
1.2. "thenable"是一个定义了then
方法的对象或函数。异步
1.3. "value"是一个合法的Javascript值(包括undefined
,一个thenable或是一个promise)。函数
1.4. "exception"是一个使用throw
声明被丢弃的value。测试
1.5. "reason"是一个指明为何一个promise被拒绝的value。
this
一个promise必须在下列三种状态之一:pending(待决),fulfilled(完成)或者rejected(拒绝)。
2.1.1. 当promise状态为pending:
2.1.1.1. 可能转换到fulfilled或者rejected状态。
2.1.2. 当promise状态为fulfilled:
2.1.2.1. 必定不会转换到任何其余状态。
2.1.2.2. 必定有一个不能改变的value。
2.1.3. 当promise状态为rejected时:
2.1.3.1. 必定不会转换到任何其余状态。
2.1.3.2. 必定有一个不能改变的reason。
这里的必定不会改变指的是不变恒等(===),但不意味着深不变性。
then
方法一个promise必须提供一个then
方法来获取它当前或是最终的value或者reason。
一个promise的then
方法接受两个参数:
promise.then(onFulfilled,onRejected)
2.2.1. onFulfilled
和onRejected
都是可选参数:
2.2.1.1. 若是onFulfilled
不是一个函数,它应当被忽略。
2.2.1.2. 若是onRejected
不是一个函数,它应当被忽略。
2.2.2. 若是onFulfilled
是一个函数:
2.2.2.1. 它必定在promise
fulfilled后才被调用,将promise
的value做为其第一个参数。
2.2.2.2. 它必定不会在promise
fulfilled前被调用。
2.2.2.3. 它的调用次数不会超过一次。
2.2.3. 若是onRejected
是一个函数:
2.2.3.1. 它必定在promise
rejected后才被调用,将promise
的reason做为其第一个参数。
2.2.3.2. 它必定不会在promise
rejected前被调用。
2.2.3.3. 它的调用次数不会超过一次。
2.2.4. onFulfilled
或者onRejected
当且仅当执行环境堆栈只包含平台代码时能够被调用。[见3.1]
2.2.5. onFulfilled
和onRejected
必须以函数的方式被调用(例如:不包含this
value)。
2.2.6. then
在同一个promise中可能被屡次调用。
2.2.6.1. 若是/当promise
被fulfilled后,全部相应的onFulfilled
调用必须按照对then
原始调用的顺序 执行。
2.2.6.2. 若是/当promise
被rejected后,全部相应的onFulfilled
调用必须按照对then
原始调用的顺 序执行。
2.2.7. then
必须返回一个promise。[见3.3]
promise2=promise1.then(onFulfilled,onRejected);
2.2.7.1. 若是onFulfilled
或者onRejected
返回一个value x
,执行如下promise解决过程:
[[Resolve]](promise2,x)
2.2.7.2. 若是onFulfilled
或者onRejected
抛出一个 exception e
,promise2
必须以e
为reason来被rejected。
2.2.7.3. 若是onFulfilled
不是一个函数,同时promise1
被fulfilled,promise2
必须使用和promise1
相同的value被fulfilled。
2.2.7.4. 若是onRejected
不是一个函数,同时promise1
被fulfilled,promise2
必须使用和promise1
相同的value被rejected。
promise解决过程表示为[[Resolve]](promise,x)
,是以一个promise和一个value为输入的抽象操做。若是x
是thenable的,同时x表现的有些像一个promise,那么解决过程试图让promise
接受x
的状态。不然,解决过程用value x
来fulfill promise。
只要promise的实现暴露了一个遵循Promises/A+的then
方法,这种thenable的特性就会使得promise的实现更具通用性,同时使得遵循了Promises/A+的promise实现能和未遵循但有可用then
方法的promise实现共存。
为了运行[[Resolve]](promise,x)
,执行如下步骤:
2.3.1. 若是promise
和x
指向同一个对象,那么以TypeError
做为reason来reject promise
。
2.3.2 若是x
是一个promise,接受它的状态[见3.4]:
2.3.2.1. 若是x
处于pending状态时,在x
处于fulfilled或者rejected状态以前,promise
必须一直保持 pending状态。
2.3.2.2. 若是/当x
处于fulfilled状态时,使用一样的value来fulfill promise
。
2.3.2.3. 若是/当x
处于rejected状态时,使用一样的reason来reject promise
。
2.3.3. 若是x
是一个对象或者函数,
2.3.3.1. 让then
变为x.then
[见3.5]
2.3.3.2. 若是取x.then
的值致使了一个exception e
的抛出,将e
做为reason来reject promise
。
2.3.3.3. 若是then
是一个函数,将x
做为this
来调用它,第一个参数为resolvePromise
,第二个参 数为rejectPromise
,其中:
2.3.3.3.1. 若是/当resolvePromise
被一个value y
调用,运行[[Resolve]](promise,y)
.
2.3.3.3.2. 若是/当rejectPromise被一个reason r
调用,用r
来reject promise
。
2.3.3.3.3. 若是resolvePromise
和rejectPromise
都被调用或者对同一参数进行了屡次调用,则第 一次调用优先,其余全部调用都被忽略。
2.3.3.3.4. 若是调用then
抛出了一个exception e
,
2.3.3.3.4.1 若是resolvePromise
或者rejectPromise
已经被调用过了,则无视。
2.3.3.3.4.2. 不然,以e
为reason来reject promise
。
2.3.3.4. 若是then
不是一个函数,用x
来fulfill promise
。
2.3.4. 若是then
不是一个对象或函数,用x
来fulfill promise
。
若是一个promise使用参与了一个循环thenable链的thenable变为resolved,例如[[Resolve]](promise,thenable)
的循环性质最终致使[[Resolve]](promise,thenable)
被再次调用,遵循上述算法将致使无限递归。鼓励但不强制要求实现检测这样的递归,并以提示信息的TypeError
做为reason来reject promise
。
3.1. 这里的平台代码指引擎,环境和promise的实现代码。实际上,这个要求确保了在then
被调用的那一轮事件循环以后的新栈中,onFulfilled
和onRejected
异步执行。可使用例如setTimeout
或setImmediate
的宏任务机制,或者例如MutationObserver
或process.nextTick
的微任务机制来实现。因为promise实现自己就是平台代码,可能自身已经包含了一个在其中调用处理程序的任务调度队列。
3.2. 在严格模式下,它们的this
是undefined
;在非严格模式下,它是一个全局对象。
3.3. 在知足全部要求的状况下实现可能容许promise1===promise2
,每一个实现都应记录是否容许以及在什么条件下容许promise2===promise1
。
3.4. 一般,只有在x
符合当前实现时,咱们才认为它是真正的promise。这一条款容许那些特定实现方式接受已知符合要求的promises状态。
3.5. 这一步首先存储了对x.then
的引用,接着测试了这个引用,随后调用这个引用,避免对于x.then
属性的屡次访问。这一预防措施对于确保访问器属性的一致性很是重要,由于访问器属性值可能在检索间改变。
3.6. 实如今thenable链的深度上不该该设置任意限制,并假定超出这一任意限制后将无限递归。只有真正的循环应该致使一个TypeError
;若是遇到了一条无限长的链上thenable各不相同,正确的行为是一直递归下去。
翻译此标准是为了便于本身后续的实现,同时加深对于Promises/A+标准的理解。按我的阅读习惯,在翻译中保留了一些在标准中解释过的专有术语。我的水平不足,翻译可能存在一些问题,如有不当之处还望指正,谢谢!