Step by step to achieve a standardized Promise Promise A +

June 2015, ES2015 (ie ES6) officially been released after a lot of attention. One very important point is that Promise was listed as a formal specification.
Prior to this a lot of libraries for asynchronous programming / callback hell classes that implement the Promise of response options, such as bluebird, jQuery's deffered Q and the famous Angular and so on.

For ease of understanding, the article is divided into three parts, each implemented as part of the characteristics of Promise, the final step by step to achieve a complete, standardized follow promise A + Promise.

Promise A + specification, Promise has three states, namely Pending (default state, waiting for the representative), Fulfilled (equal success), Rejected (for failure).

Take a look at the usage of Promise, and what features it has.

var fn = new Promise(function (resolve, reject) {    
    // 异步操作    
    setTimeout(function() {        
        resolve('resolve 01')        
        // 由于reslove和 reject 是互斥的,因为已经调用了 resolve,这里reject不会执行 
        reject('reject 01')
    }, 500)
})
fn().then(function (data) {
    console.log('成功1:', data)
    return new Promise(function (resolve, reject) {
        reject('reject 02')
    }
)}, function (err) {
    console.log('失败1:', err)
})
.then(function (data) {
    console.log('成功2:', data)
}, function (err) {
    console.log('失败2:', err)
}).then(function (data) {
    console.log('成功2:', data)}, function (err) {
    console.log('失败2:', err)
})

result:


You can see, Promise usually have these features:

①, Promise class has then method, then the method has two parameters, namely, the callback Promise of success and failure, and the two are mutually exclusive, call one of them, the other will not be executed

②, Promise to support chained calls, then the return value can be a Promise, can also be a common value, if it is a common value, then the next parameter of success callback function as it will

③, Promis extension there are other methods

Some did not say a bunch, following began to realize this thing right ~

=================================================

First, to achieve Promise class

=> Promise method has then:

var Promise = function (executor) {
    console.log('证明不是用的原生 Promise')
    var _this = this
    this.status = 'pending'
     // 默认状态,可以转化为 resolved 和 rejected
    this.successVal = undefined
    this.failVal = undefined

    // 执行了成功或失败后,要将状态对应修改成成功和失败
    function resolve (val) {
        if ( _this.status === 'pending' ) {
            _this.status = 'resolved'
            _this.successVal = val
        }
    }
    function reject (val) {
        if ( _this.status === 'pending' ) {
            _this.status = 'rejected'
            _this.failVal = val
        }
    }

    try {
        // 应该还记得,Promise 的参数是一个函数吧,我们称之为 executor(执行器)
        // 同时这个函数接收2个参数,分别是成功和失败的回调函数
        executor(resolve, reject)
    } catch (e) {
        // 如果发生异常,直接reject捕获
        reject(e)
    }
}
// then 方法接收2个参数,分别是成功和失败的回调函数
Promise.prototype.then = function (onFulfilled, onRejected) {
    var _this = this    
    // 显然要根据当前状态来执行成功或失败的回调了
    if ( _this.status === 'resolved' ) {
        onFulfilled(_this.successVal)
    }
    if ( _this.status === 'rejected' ) {
        onFulfilled(_this.failVal)
    }
}
To try the effect:

var fn = new Promise(function (resolve, reject) {
    resolve('oooook~')
}) 
fn.then(function (data) {
    console.log('success: ', data)}, function (err) {
    console.log('err: ', err)
})

result:


The result looks beautiful. But if the change following this happen?

var fn = new Promise(function (resolve, reject) {
    setTimeout(function () {
        resolve('oooook~')
    }, 500)
}) 
fn.then(function (data) {
    console.log('success: ', data)
}, function (err) {
    console.log('err: ', err)
})
result:


ok, the question is, Promise effort needed to engage not only do synchronous calls out, after all, after the front end with ajax will develop to be so prosperous today, so we need to support asynchronous Promise.

Modified as follows (the comment is a description of the new code):

var Promise = function (executor) {
    console.log('证明不是用的原生 Promise 的一句废话')
    var _this = this    this.status = 'pending'
     // 默认状态,可以转化为 resolved 和 rejected
    this.successVal = undefined
    this.failVal = undefined
    // ----------------- 表示新增代码 --------------------    // 用于存放成功和失败的回调
    this.onFulfilledList = []
    this.onRejectedList = []

    function resolve (val) {
        if ( _this.status === 'pending' ) {
            _this.status = 'resolved'
            _this.successVal = val
            // -------------- 执行所有的成功回调 ---------------
            _this.onFulfilledList.forEach(function(fn){
                fn()
            })
        }
    }
    function reject (val) {
        if ( _this.status === 'pending' ) {
            _this.status = 'rejected'
            _this.failVal = val
            // -------------- 执行所有的失败回调 ---------------
            _this.onRejectedList.forEach(function(fn){
                fn()
            })
        }
    }
    try {
        executor(resolve, reject)
    } catch (e) {
        reject(e)
    }
}
Promise.prototype.then = function (onFulfilled, onRejected) {

    var _this = this

    if ( _this.status === 'resolved' ) {
        onFulfilled(_this.successVal)
    }
    if ( _this.status === 'rejected' ) {
        onFulfilled(_this.failVal)
    }

    // ----------------- 对异步调用的处理 -------------------
    // 说明:如果是异步调用,走到 then 方法里的时候,status 还没有被修改,仍然
    // 是 pending 状态,所以这时候需要再回去执行 executor 里的对应方法,而对应的
    // 方法会将对应的存放回调的 list 里的方法执行(类似发布-订阅模式一样的处理)
    if ( _this.status === 'pending' ) {
        _this.onFulfilledList.push(function () {
            onFulfilled(_this.successVal)
        })
        _this.onRejectedList.push(function () {
            onRejected(_this.failVal)
        })
    }
}
Look at the results:


Now has the support asynchronous ~


I heard that you are in big black Star-Lord? Star-Lord so adorable, you have the heart to do



Next: step by step to achieve a Promise A + Promise of the two specifications: Promise chained calls


Guess you like

Origin www.cnblogs.com/homehtml/p/11794924.html