Promise用法
在项目中用到异步请求ajax,想到用promise来解决,之前用过但是已经很久了,还是忘了一些,重新熟悉了一下整理一份简要文档。
Promise,就是一个对象,用来传递异步操作的消息
Promise 对象代表一个异步操作,有三种状态:Pending(进行中)、Resolved(已完成,又称 Fulfilled)和 Rejected(已失败)。
如果异步操作成功,则用 resolve 方法将 Promise 对象的状态,从「未完成」变为「成功」(即从 pending 变为 resolved);
如果异步操作失败,则用 reject 方法将 Promise 对象的状态,从「未完成」变为「失败」(即从 pending 变为 rejected)。
var promise = new Promise(function(resolve, reject) {
if (/* 异步操作成功 */){
resolve(value);
} else {
reject(error);
}
});
promise.then(function(value) {
// success
}, function(value) {
// failure
});
可以简要看看promise的源码
var Promise = function() {
this.doneList = [];
this.failList = [];
this.state = ‘pending‘;
};
Promise.prototype = {//几种常用方法
constructor: ‘Promise‘,
resolve: function() {
this.state = ‘resolved‘;
var list = this.doneList;
for(var i = 0, len = list.length; i < len; i++) {
list[0].call(this);
list.shift();
}
},
reject: function() {
this.state = ‘rejected‘;
var list = this.failList;
for(var i = 0, len = list.length; i < len; i++){
list[0].call(this);
list.shift();
}
},
done: function(func) {
if(typeof func === ‘function‘) {
this.doneList.push(func);
}
return this;
},
fail: function(func) {
if(typeof func === ‘function‘) {
this.failList.push(func);
}
return this;
},
then: function(doneFn, failFn) {
this.done(doneFn).fail(failFn);
return this;
},
always: function(fn) {
this.done(fn).fail(fn);
return this;
}
};
function when() {
var p = new Promise();
var success = true;
var len = arguments.length;
for(var i = 0; i < len; i++) {
if(!(arguments[i] instanceof Promise)) {
return false;
}
else {
arguments[i].always(function() {
if(this.state != ‘resolved‘){
success = false;
}
len--;
if(len == 0) {
success ? p.resolve() : p.reject();
}
});
}
}
return p;
}
业务中的代码实现方式如下:在两次异步请求成功之后,再调用then的方法
return (dispatch, getState)=> {
let getDataFunc = function(data) {
return new Promise(function(resolve, reject){
if(!data) {
return resolve(null);
}
return requestJsonp({
url: ‘‘,
data: data,
}, json=>{
resolve(json);
}, err=>{
resolve(null);
});
});
};
return Promise.all([getDataFunc(data), getDataFunc(compareData)]).then((json)=>{
if(!json[0] && !json[1]) {
dispatch({
type: DATA_ERR
});
} else {
dispatch({
type: REFRESH_GRAPH,
data: json
});
}
});
};
现今流行的各大js库,几乎都不同程度的实现了Promise,如dojo,jQuery、Zepto等,它们暴露出来的大都是Deferred对象,以jQuery(Zepto类似)为例:方法更加简洁方便
function getImg(url) {
var def = $.Deferred();
var img = new Image();
img.onload = function() {
def.resolve(this);
};
img.onerror = function(err) {
def.reject(err);
};
img.src = url;
return def.promise();
};
推荐一部书 promise迷你书,很薄的一本,
http://liubin.org/promises-book/javascript-promise-book.pdf
时间: 2024-10-13 00:19:16