多应用+插件架构,代码干净,二开方便,首家独创一键云编译技术,文档视频完善,免费商用码云13.8K 广告
**在vue项目中,和后台交互获取数据这块,我们通常使用的是axios库,它是基于promise的http库,可运行在浏览器端和node.js中。他有很多优秀的特性,例如拦截请求和响应、取消请求、转换json、客户端防御cSRF等,下面是个完整实例...** ``` import axios from 'axios'; import emd5 from 'js-md5'; import cx from './config.js'; const isToken = cx.isToken || false; const tokenCacheKey = cx.tokenCacheKey; const tokenSecret = cx.tokenSecret; const tokenCreate = cx.apiToken; const tokenRefresh = cx.apiTokenRefresh; const filterArray = [tokenCreate,tokenRefresh]; const apiConfig = { baseURL : cx.baseUrl, timeout : cx.timeOut, withCredentials : true /* 表示跨域请求时是否需要使用凭证 默认false */ }; let apiQueue = []; /* 请求队列 */ let api = axios.create(apiConfig); /* 请求拦截器 */ api.interceptors.request.use( config => { if(isToken === false){ return config; } _pushQueue(config) let data = _token(config); return data; }, error => { return Promise.reject(error); } ); /* 响应拦截器 */ api.interceptors.response.use( response => { return _response(response.data); }, error => { return Promise.reject(error); } ); /** * 处理拦截器响应 * @param {Object} res */ function _response(res){ try{ if(isToken === false){ return res; } /* 可以增加其他拓展 */ switch (res.code){ case '10003' || '10004': return _tokenRefresh().then(res=>{ return _cacheRequest(res) }) break; default : apiQueue = []; return res; break; } }catch(e){ return Promise.reject(e) } } /* 刷新token */ function _tokenRefresh(){ let token = window.localStorage.getItem(tokenCacheKey), author = {Authorization : `bearer ${token}`}; return new Promise((resolve,reject)=>{ apiConfig.headers = author; axios.create(apiConfig).get(tokenRefresh).then(res=>{ if(res.data.code == '200'){ token = res.data.data.refresh_token; window.localStorage.setItem(tokenCacheKey,token); if(apiQueue.length == 0){ reject('没有可以执行的方法'); } resolve(apiQueue[0]) }else{ reject(res.data.msg); } }).catch(error=>{ reject(error); }) }); } /* 获取token */ function _token(config){ let token = window.localStorage.getItem(tokenCacheKey); if(token != '' && token != 'undefined' && token !== null){ config.headers.Authorization = `bearer ${token}` return config; }else{ let deviceId = uni.getSystemInfoSync().deviceId, secret = `${deviceId}&${tokenSecret}`; return axios.get(tokenCreate,{ params : { mac : deviceId, secret : emd5(secret) } }) .then(response => { token = response.data.data.token; window.localStorage.setItem(tokenCacheKey,token); config.headers.Authorization = `bearer ${token}` return config; }) .catch(error => { return Promise.reject(error); }) } } /* 添加待执行方法进入队列 */ function _pushQueue(config){ if(true === filterArray.includes(config.url)){ return false; } apiQueue.push({ url : config.url, method : config.method, params : config.params, data : config.data }); } /** * @param {Object} config * @description 重新发送队列中的缓存的请求,为避免多余发送,只取第一个且发送成功后清空队列 */ function _cacheRequest(config){ let request = {url:config.url,method:config.method}; if(config.method == 'get'){ request.params = config.params; }else if(config.method == 'post'){ request.data = config.data; } return api.request(request) .then(result => { apiQueue = []; return Promise.resolve(result); }).catch(error => { return Promise.reject(error) }) } /** * @param {String} url * @param {Array} data * @description 对外暴露的POST方法 */ let cxPost = (url,data)=>{ return _cacheRequest({ url : url, method : 'post', data : data }); } /** * @param {String} url * @param {Array} data * @description 对外暴露的GET方法 */ let cxGet = (url,data)=>{ return _cacheRequest({ url : url, method : 'get', params : data }); } export {cxGet,cxPost}; ```