UNPKG

@10yun/cv-js-utils

Version:

常用 js-utils 工具类库

530 lines (516 loc) 14.9 kB
/** * 是否在数组里 * @param key * @param array * @param regular * @return {Boolean|*} */ function urlInArray(key, array, regular = false) { if (regular) { return !!array.find((item) => { if (item && item.indexOf('*')) { const rege = new RegExp('^' + item.replace(/[-\/\\^$+?.()|[\]{}]/g, '\\$&').replace(/\*/g, '.*') + '$', 'g'); if (rege.test(key)) { return true; } } return item == key; }); } else { return array.includes(key); } } function checkUrlParse(need_url, base_url) { let all_url = ''; // /(http|https):\/\/([\w.]+\/?)\S*/.test(url) if (need_url.includes('http://') || need_url.includes('https://')) { all_url = need_url; } else { all_url = base_url + need_url; } /** * 使用正则表达式进行过滤 * TODO 过滤除了 https:// 和 http:// 以外的 // 和 /// ,但保留 ? 后面的内容 * all_url = all_url.replace(/^(https?:\/\/[^/]+)\/+/g, '$1/'); */ /** * * 过滤除了 https:// 和 http:// 以外的 // 和 /// */ all_url = all_url.replace(/([^:]\/)\/+/g, '$1'); return all_url; } // 如果你想重新规定返回的数据格式,那么可以借助 response 参数,如: const responseField = { statusName: 'status', // 规定数据状态的字段名称,默认:code statusCode: 200, // 规定成功的状态码,默认:0 msgName: 'msg', // 规定状态信息的字段名称,默认:msg countName: 'total', // 规定数据总数的字段名称,默认:count dataName: 'data' // 规定数据列表的字段名称,默认:data }; /* * 收集错误信息 */ const EnumStatusToTitle = { 400: '请求错误', 400: '无效请求', 401: '未经授权', 402: '支付请求', 403: '拒绝访问', 404: '请求出错', 408: '请求超时', 422: '请求验证', 500: '响应错误', 501: '服务未实现', 502: '网络错误', 503: '服务不可用', 504: '网络超时', 505: 'HTTP版本不受支持' }; const EnumStatusToMsg = { 400: '参数错误', 401: '没有权限,请变更请求', 402: '支付错误', 403: '检查请求域名是否添加了域名白名单', 404: '未找到该请求', 408: '网络异常,请检查网络设置', 422: '参数验证错误', 504: '请求超时,请刷新重试', 500: '请检查网络或服务器' // 服务器错误 // 服务器异常,请联系管理员 // 没有配置服务器地址 }; export function responseInfoParse(status, message) { status = parseInt(status); let lastTitle = '提示'; let lastMsg = '请检查网络或联系管理员'; // 程序异常, // 状态码 - 匹配 - 标题 if (EnumStatusToTitle[status]) { lastTitle = EnumStatusToTitle[status]; } // 状态码 - 匹配 - 信息 if (EnumStatusToMsg[status]) { lastMsg = EnumStatusToMsg[status]; } return { title: lastTitle, status: status, message: lastMsg }; } class RequestClass { constructor(options = {}) { this.flagMap = options.flagMap || {}; this.flagAuth = options.flagAuth || {}; this.flagCurr = ''; this.baseURL = options.baseURL || ''; this.baseMock = options.baseMock || ''; this.requests = Object.assign({}, options.requests || {}); this.requestTemp = {}; this.headers = Object.assign({}, options.headers || {}); this.headerTemp = {}; this.configs = Object.assign({}, options.configs || {}); this.configTemp = {}; // 临时 this.customs = Object.assign({}, options.customs || {}); // 自定义参数 this.customTemp = {}; // 临时 // 需要加密的url this.encryptURL = options.encryptURL || []; this.encryptFlag = false; this.retries = 3; this.debugState = options.debug || false; this.requestHandle = null; /* 新创建 http 实例配置 */ this._initReqHandle(options); } debugLog() { if (this.debugState) { console.log('[调试]', ...arguments); } } /* 初始化 request 句柄 */ _initReqHandle(options) { // timeout: options.timeout || 5000, // request timeout // // 表示跨域请求时是否需要使用凭证; // // 开启withCredentials后,服务器才能拿到你的cookie // // 当然后端服务器也要设置允许你获取你开启了才有用 // // withCredentials: true, // 开启跨域身份凭证 // retry: 2 } /** * 设置API */ setApiFlag(options) { this.flagMap = options || {}; return this; } appendApiFlag(options) { this.flagMap = Object.assign({}, this.flagMap, options || {}); return this; } setApiAuth(options) { this.flagAuth = options || {}; return this; } appendApiAuth(options) { this.flagAuth = Object.assign({}, this.flagAuth, options || {}); return this; } /** * 设置默认header参数 * @param {Object} options * @return {Class} this */ setDefHeaders(options) { this.headers = Object.assign({}, this.headers, options || {}); return this; } setHeaders(options) { this.headerTemp = Object.assign({}, this.headerTemp, options || {}); return this; } getHeaders() { return this.headers; } /** * 设置默认requests参数 * @param {Object} options * @return {Class} this */ setDefRequests(options) { this.requests = Object.assign({}, this.requests, options || {}); return this; } setRequests(options) { this.requestTemp = Object.assign({}, this.requestTemp, options || {}); return this; } /** * @function setOptions 设置临时配置 * @param {Object} options - 参数 * @return {Class} this */ setOptions(options = {}) { this.configTemp = Object.assign({}, this.configTemp, options || {}); return this; } /** * @function setCustom 设置临时自定义参数 * @param {Object} options - 参数 * @return {Class} this */ setCustom(options) { this.customTemp = Object.assign({}, this.customTemp, options || {}); return this; } /** * 设置 signal */ setSignal(signal) {} /** * 加密 */ encrypt() { this.encryptFlag = true; return this; } __encryp_parse(url) { let encryptFlag = false; if (this.encryptURL && urlInArray(url, this.encryptURL, true)) { encryptFlag = true; } if (this.encryptFlag) { encryptFlag = true; } if (encryptFlag) { // 是 Windows Xp, Vista, 7, 8 系统,不支持加密 const userAgent = window.navigator.userAgent; if ( /Windows NT 5.1|Windows XP/.test(userAgent) || userAgent.indexOf('Windows NT 6.0') !== -1 || userAgent.indexOf('Windows NT 6.1') !== -1 || userAgent.indexOf('Windows NT 6.2') !== -1 ) { encryptFlag = false; } } return encryptFlag; } cancelRequest(requestId) { if (!requestId) { return 0; } let __ajaxList = []; let num = 0; __ajaxList.forEach((val, index) => { if (val.id === requestId) { num++; if (val.request) { val.request.abort(); } } }); if (num > 0) { __ajaxList = __ajaxList.filter((val) => val.id !== requestId); } return num; } /** * 请求方式 */ __parse_method_type(type) { let last_type = type; return last_type; } /** * 调用 API 统一 请求 方法 * * @author ctocode-zhw * @version 2018-12-20 * @param apiUrl 不需要域名,域名统一拼接,只填写相关请求接口 【必须】 * @param reqData 提交参数 * @return * */ async apiAll(type, apiUrl, reqData) { let request_url = checkUrlParse(apiUrl, this.baseURL); /** * 判断是否加密 */ let encryptFlag = this.__encryp_parse(apiUrl); /** * 最后 type */ let last_type = this.__parse_method_type(type); /** * url是否需要鉴权 */ let curr_auth_str = this.flagAuth[this.flagCurr] || null; let auth_data = {}; if (curr_auth_str) { auth_data = curr_auth_str.split(',').reduce((acc, pair) => { const [key, value] = pair.split('='); acc[key] = value; return acc; }, {}); } /** * 合并变量 */ let mergeHeaders = Object.assign({}, this.headers, this.headerTemp, {}); let mergeRequests = Object.assign({}, this.requests, this.requestTemp, reqData || {}); let mergeConfigs = Object.assign({}, this.configs, this.configTemp, {}); let mergeCustoms = Object.assign({}, this.customs, this.customTemp, { flag: this.flagCurr, auth: auth_data, time: Math.floor(Date.now() / 1000) // 当前时间戳(秒) }); // 1. 执行请求拦截器 // 2. 发起请求 let responseInfo = {}; if (last_type == 'UPLOAD') { mergeHeaders['Content-Type'] = 'multipart/form-data'; } else if (last_type == 'DOWNLOAD') { /* 文件下载 */ } else if (last_type == 'MOCK') { } else { let otherMethod = ['GET', 'POST', 'PUT', 'PATCH', 'DELETE']; if (!otherMethod.includes(last_type)) { console.error('类型错误:', last_type); return {}; } return this.ExternalRequestFunc(request_url, { // baseURL: this.baseURL || '', method: last_type, params: mergeRequests, headers: mergeHeaders // headers: { // 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8', // 'Accept': 'application/json, text/javascript, */*; q=0.01', // } }) .then((response) => { const responseError = response?.error._rawValue || null; const responseData = response?.data._rawValue || null; const responseStatus = response?.status._rawValue || ''; if (responseStatus == 'error') { return this.netResponseError({ status: 500, message: responseStatus }); } if (responseData && responseStatus == 'success') { return this.netResponseOK({ status: 200, data: responseData, message: responseStatus }); } }) .catch((error) => { return Promise.reject(error); }); } } flagMockPost() { const argumentsArr = arguments; return this.unifyApi('flag', 'MOCK', argumentsArr); } flagMockGet() { const argumentsArr = arguments; return this.unifyApi('flag', 'MOCK', argumentsArr); } urlMockPost() { const argumentsArr = arguments; return this.unifyApi('url', 'MOCK', argumentsArr); } urlMockGet() { const argumentsArr = arguments; return this.unifyApi('url', 'MOCK', argumentsArr); } /** * GET 请求 */ flagGet() { const argumentsArr = arguments; return this.unifyApi('flag', 'GET', argumentsArr); } urlGet() { const argumentsArr = arguments; return this.unifyApi('url', 'GET', argumentsArr); } /** * POST 请求 */ flagPost() { const argumentsArr = arguments; return this.unifyApi('flag', 'POST', argumentsArr); } urlPost() { const argumentsArr = arguments; return this.unifyApi('url', 'POST', argumentsArr); } /** * PUT 请求 */ flagPut() { const argumentsArr = arguments; return this.unifyApi('flag', 'PUT', argumentsArr); } urlPut() { const argumentsArr = arguments; return this.unifyApi('url', 'PUT', argumentsArr); } /** * PATCH 请求 */ flagPatch() { const argumentsArr = arguments; return this.unifyApi('flag', 'PATCH', argumentsArr); } urlPatch() { const argumentsArr = arguments; return this.unifyApi('url', 'PATCH', argumentsArr); } /** * DELETE 请求 */ flagDel() { const argumentsArr = arguments; return this.unifyApi('flag', 'DELETE', argumentsArr); } urlDel() { const argumentsArr = arguments; return this.unifyApi('url', 'DELETE', argumentsArr); } /* 文件上传通用 */ flagUpload() { const argumentsArr = arguments; return this.unifyApi('flag', 'UPLOAD', argumentsArr); } urlUpload() { const argumentsArr = arguments; return this.unifyApi('url', 'UPLOAD', argumentsArr); } /* 图片上传通用 */ flagUpImg() { const argumentsArr = arguments; return this.unifyApi('flag', 'UPLOAD', argumentsArr); } urlUpImg() { const argumentsArr = arguments; return this.unifyApi('url', 'UPLOAD', argumentsArr); } /** * 统一请求 */ unifyApi(flagOrUrl, methodType, argumentsArr) { let _this = this; let argNum = argumentsArr.length || 0; if (argNum <= 0 || argNum > 3) { let errorMsg = `-- ${methodType} : 参数为(1-3)个---`; return new Promise((resolve, reject) => { return reject({ message: errorMsg }); }); } let apiUrl = ''; let apiUrlNoMsg = ''; if (flagOrUrl == 'flag') { let apiFlag = argumentsArr[0]; if (typeof apiFlag === 'string') { apiFlag = apiFlag || ''; apiUrl = apiFlag == '' ? '' : this.flagMap[apiFlag] || ''; } apiUrlNoMsg = ' flag' + methodType + ':传入的标示 { ' + `${apiFlag}` + ' },未匹配到 apiUrl '; this.flagCurr = apiFlag; } if (flagOrUrl == 'url') { apiUrl = argumentsArr[0]; if (typeof apiUrl === 'string') { apiUrl = apiUrl || ''; } apiUrlNoMsg = ' 未匹配到 apiUrl '; } if (apiUrl == '') { return new Promise((resolve, reject) => { return reject({ message: apiUrlNoMsg }); }); } // 如果传回一个 if (argNum == 1) { return function (reqData) { return _this.apiAll(methodType, apiUrl, reqData); }; } else if (argNum == 2 || argNum == 3) { let reqData = {}; let arg2Val = argumentsArr[1]; let arg2Type = Object.prototype.toString.call(arg2Val); // let argType2_2 = typeof argumentsArr[1] === 'object'; if (arg2Type === '[object String]' || arg2Type === '[object Number]') { let isEndIdStr = String(arg2Val).trim(); if (/^\d+$/.test(isEndIdStr)) { if (!apiUrl.endsWith('/')) { apiUrl += '/'; } apiUrl += isEndIdStr; // 拼接时保留大整数精度 } if (argNum == 3) { let arg3Val = argumentsArr[2]; let arg3Type = Object.prototype.toString.call(arg3Val); if (arg3Type === '[object Object]') { reqData = arg3Val || {}; } } } else if (arg2Type === '[object Object]') { reqData = arg2Val || {}; } else if (arg2Type === '[object FormData]') { reqData = arg2Val || new FormData(); } return _this.apiAll(methodType, apiUrl, reqData); } else { return new Promise((resolve, reject) => { return reject({ message: ' 请求错误 ' }); }); } } } export default RequestClass;