/**
* @Author : Xiao Xiang Lun
* @Date : 2023-11-15 15:57:06
* @LastEditors : snowlove xiaoxl@botech.com.cn
* @LastEditTime : 2023-11-15 16:31:45
* @FilePath : /react/demo/src/views/DemoStoreTwo/fetchReq.js
* @Environment : mac node v16.3.0
* @Description :
* @关注作者请访问 https://snowlove.synology.me:5
* @备用地址:https://nas.snowlove.top:5
*/
/*
http([config])
+ url 请求地址
+ method 请求方式 *GET/DELETE/HEAD/OPTIONS/POST/PUT/PATCH
+ credentials 携带资源凭证 *include/same-origin/omit
+ headers:null 自定义的请求头信息「格式必须是纯粹对象」
+ body:null 请求主体信息「只针对于POST系列请求,根据当前服务器要求,如果用户传递的是一个纯粹对象,我们需要把其变为urlencoded格式字符串(设定请求头中的Content-Type)...」
+ params:null 设定问号传参信息「格式必须是纯粹对象,我们在内部把其拼接到url的末尾」
+ responseType 预设服务器返回结果的读取方式 *json/text/arrayBuffer/blob
+ signal 中断请求的信号
-----
*/
// import qs from 'https://cdn.bootcdn.net/ajax/libs/qs/6.11.2/qs.min.js';
const class2type = {},
toString = class2type.toString,
hasOwn = class2type.hasOwnProperty,
isPlainObject = function isPlainObject(obj) {
let proto, Ctor;
if (!obj || toString.call(obj) !== "[object Object]") return false;
proto = Object.getPrototypeOf(obj);
if (!proto) return true;
Ctor = hasOwn.call(proto, "constructor") && proto.constructor;
return typeof Ctor === "function" && Ctor === Object;
},
qsStringify = function qsStringify(obj) {
const params = [];
for (const key in obj) {
if (obj.hasOwnProperty(key)) {
const value = obj[key];
const encodedKey = encodeURIComponent(key);
const encodedValue = encodeURIComponent(value);
params.push(`${encodedKey}=${encodedValue}`);
}
}
return params.join('&');
}
/* 核心方法 */
const http = function http(config) {
if (!isPlainObject(config)) config = {};
const controller = new AbortController();
config = Object.assign({
url: '',
method: 'GET',
credentials: 'include',
headers: null,
body: null,
params: null,
responseType: 'json',
signal: (controller && controller.signal) || null,
}, config);
if(config.abort || config.abort instanceof Promise) {
config.abort().then((_)=>controller.abort())
}
if (!config.url) throw new TypeError('url must be required');
if (!isPlainObject(config.headers)) config.headers = {};
if (config.params !== null && !isPlainObject(config.params)) config.params = null;
let { url, method, credentials, headers, body, params, responseType, signal } = config;
// 处理问号传参
if (params) {
url += `${url.includes('?') ? '&' : '?'}${qsStringify(params)}`;
}
// 处理请求主体信息:按照我们后台要求,如果传递的是一个普通对象,我们要把其设置为urlencoded格式「设置请求头」?
if (isPlainObject(body)) {
body = qsStringify(body);
headers['Content-Type'] = 'application/x-www-form-urlencoded';
}
// 发送请求
method = method.toUpperCase();
config = {
method,
credentials,
headers,
cache: 'no-cache',
signal
};
if (/^(POST|PUT|PATCH)$/i.test(method) && body) config.body = body;
return fetch(url, config)
.then(response => {
let { status, statusText } = response;
if (/^(2|3)\d{2}$/.test(status)) {
// 请求成功:根据预设的方式,获取需要的值
let result;
switch (responseType.toLowerCase()) {
case 'text':
result = response.text();
break;
case 'arraybuffer':
result = response.arrayBuffer();
break;
case 'blob':
result = response.blob();
break;
default:
result = response.json();
}
return result;
}
// 请求失败:HTTP状态码失败
return Promise.reject({
code: -100,
status,
statusText
});
})
.catch(reason => {
return Promise.reject(reason); //统一处理完提示后,在组件中获取到的依然还是失败
});
};
/* 快捷方法 */
["GET", "HEAD", "DELETE", "OPTIONS"].forEach(item => {
http[item.toLowerCase()] = function (url, config) {
if (!isPlainObject(config)) config = {};
config['url'] = url;
config['method'] = item;
return http(config);
};
});
["POST", "PUT", "PATCH"].forEach(item => {
http[item.toLowerCase()] = function (url, body, config) {
if (!isPlainObject(config)) config = {};
config['url'] = url;
config['method'] = item;
config['body'] = body;
return http(config);
};
});
export default http;
调用方法 如需中断链接 传入abort回调 在其中重写逻辑 注意返回一个promise
http.get(' https://snowlove.synology.me:6002/mock/6553259ddb7e05001d99be09/example/query',{
abort:()=>new Promise((reslove)=>{
console.log("abort1")
reslove(true)
})
}).then(res=>{
console.log(res)
}).catch(err=>{
console.log("捕捉主动终止错误")
})
http.get(' https://snowlove.synology.me:6002/mock/6553259ddb7e05001d99be09/example/query',{
abort:()=>new Promise((reslove)=>{
console.log("abort2")
setTimeout(() => {
reslove(true)
}, 1000);
})
}).then(res=>{
console.log(res)
}).catch(err=>{
console.log("捕捉错误2")
})
/**
* abort1
* abort2
* 捕捉错误
*/
评论 (0)