fetch+promise
我知道的是针对一个请求的,且返回promise对象,then中以resolve接收response,下面先简单介绍下组合使用场景
一、结合超时处理
//基本配置参数
let defaultOption = {
timeout: 5000,
method: 'post',
data: null,
before: () => { }
after: () => { },
success: (result) => { console.log(`request success, result is ${result}`) },
error: (errorMsg, errorStatus) => { console.log(`request error, error is ${errorMsg}`) }
}
//获取fetch配置参数,可以参考网上相关说明
const getFetchOption = (_fo = {}) => {
let fo = {
credentials: 'same-origin', // 提交的时候包含
mode: 'cors', // 支持跨域
method: 'post',
body: null,
headers: {
"Accept": "application/json", // 返回值为json
"Content-Type": "application/json;charset=utf-8"
}
}
if(_fo.body) {
if(typeof _fo.body == 'object') _fo.body = JSON.stringify(_fo.body);
}
return Object.assign(fo, _fo);
}
//包装fetch与timeout
const getRequestPromise = (url, option = {}) => {
let _option = Object.assign({}, defaultOption, option);
let _timeout = null;
//超时promise
_option.before();
let timeoutPromise = new Promise((resolve, reject) => {
_timeout = setTimeout( () => {
throw new Error('timeout');
}, _option.timeout );
});
let fetchPromise = new Promise((resolve, reject) => {
fetch(url, getFetchOption({ method: _option.method, body: _option.data }))
.then(
response => {
if(response.status >= 200 && response.status <= 300) return response.json();
else {
let error = new Error(response.status);
error.response = response;
reject(error);
}
}
)
.then(
result => resolve(result)
)
.finally(
() => {
clearTimeout(_timeout);
_option.after();
}
)
});
let _promise = Promise.race([fetchPromise, timeoutPromise]);
return { _promise: _promise, _option: _option };
}
二、单个请求
//请求(单个)
const request(url, option = {}) {
let { _promise, _option } = getRequestPromise();
_promise.then(
result => _option.success(result)
).catch(
error => _option.error(error)
)
}
//demo
request('your request url', /*{ ... }*/)
三、多个请求
//请求(多个)
const requests(...param) {
let promises = param.map((_param, _index) => {
let { url, option } = _param;
let { _promise, _option } = getRequestPromise(uri, option);
return new Promise((resolve, reject) => {
_promise.then(
result => resolve({ result: result, success: _option.success })
).catch(
error => reject({er: error, error: _option.error})
)
});
});
Promise.all(promises)
.then(
objs => { objs.forEach((obj, index) => { obj.success && obj.success(obj.result) }) }
)
.catch(
e => { e.error && e.error(e.er) }
)
}
//demo
requests({url: 'your request url', /*option: { ... }*/}, {url: 'your request url', /*option: { ... }*/}...)