Axios封装之取消重复请求和接口缓存

2022-12-22 0 1,060

在平常的单网页工程项目里,我们的确碰触过axios库,两个功能强大、简约且高效率,采用Promise管理工作触发器,挥别现代callback形式的http库。

前段天数有位工程项目里USB调阅的振幅较为高,USB堆栈长,接着等候数据的天数是伤痛的折磨,不光是连串有关连的统计数据可视化,每天关上网页我都似曾相识欲死的觉得。历经几番反思改建后,去除USB这类的速率,对网页的简洁Ins13zD了许多,因此那时就和我们撷取呵呵,是不是PCB伊瓦诺Axios,中止多次重复允诺和USB内存。

加装Axios

npm install axios

Axios基本上实用性

子目录下增建axios.config.js文档,先载入允诺圣夫龙,积极响应圣夫龙,当中要不光注意USB允诺失利的信息处置,依照status推论与否要展开附加的处置,比如上面范例推论statue为401则去除token,再次登入,假如有error.message 就回到原始统计数据标识符100002,用作网页推论表明错误信息。

/** axiosPCB 允诺截击、积极响应截击 */ import axios from axios; import router from ../router; import qs from qs; /** 增设post允诺头 */ instance.defaults.headers.post[Content-Type] = application/x-www-form-urlencoded; /** 允诺圣夫龙*/ instance.interceptors.request.use( (config) => { let token = window.localStorage.getItem(token); token = token ? token : ; token && (config.headers.Authorization = token); return config; }, (error) => Promise.reject(error) ); /** 积极响应拦截器 */ instance.interceptors.response.use( (res) => { return Promise.resolve(res); }, // 允诺失利 (error) => { if (error) { let { response } = error; /** 浏览器报错 */ if (response) { /** 登入过期 */ if (response.status == 401) { localStorage.removeItem(token); router.replace(/login); } } if (error.message) { if (typeof error.message === string) { response = { code: 100002, message: error.message }; } } else { response = {}; } return Promise.resolve(response ? response : { code: 100002 }); } else { return Promise.resolve({ code: 100002 }); } } ); export default instance;
中止多次重复USB

增建两个数组taskList用作存储USB允诺任务堆栈,USB允诺流程如下图。比如允诺AUSB的时候,先推论AUSB与否存在于taskList里,如若存在则axios.CancelToken方法中止前两个AUSB,接着往堆栈里增加本次AUSB,等到允诺完成的时候,再将AUSB移除taskList,以此类推就完成两个动态任务堆栈啦。

Axios封装之取消重复请求和接口缓存
/** axiosPCB 允诺截击、积极响应截击 */ import axios from axios; import router from ../router; const CancelToken = axios.CancelToken, apiCach = { taskList: [] /** 允诺任务列表 */, /** 新增任务 */ addTask(config, cancelToken) { this.taskList.push({ original: `${config.url}&${config.method}`, cancelToken }); }, /** 删除任务 */ deleteTask(config, start, cancelToken) { let cancel = false; for (let i in this.taskList) { if (this.taskList[i][original] == `${config.url}&${config.method}`) { this.taskList[i].cancelToken(); this.taskList.splice(i, 1); cancel = true; break; } } }, }, /** 创建axios实例 */ instance = axios.create({ timeout: 1000 * 12, }); /** 增设post允诺头 */ instance.defaults.headers.post[Content-Type] = application/x-www-form-urlencoded; /** 允诺圣夫龙*/ instance.interceptors.request.use( (config) => { config.cancelToken = new CancelToken((c) => { /** 删除任务 */ apiCach.deleteTask(config, true, c); /** 新增任务*/ apiCach.addTask(config, c); }); config.headers.expirationTime = void 0; let token = window.localStorage.getItem(token); token = token ? token : ; token && (config.headers.Authorization = token); return config; }, (error) => Promise.reject(error) ); /** 积极响应圣夫龙 */ instance.interceptors.response.use( (res) => { apiCach.deleteTask(res.config, false); return Promise.resolve(res); }, // 允诺失利 (error) => { if (error) { let { response } = error; /** 浏览器报错 */ if (response) { if (response.status == 401 || response.status == 403) { localStorage.removeItem(token); router.replace(/login); } } if (error.message) { if (typeof error.message === string) { response = { code: 100002, message: error.message }; } } else { response = {}; } return Promise.resolve(response ? response : { code: 100002 }); } else { return Promise.resolve({ code: 100002 }); } } ); export default instance;
USB缓存,避免资源过度消耗

对调用振幅高、统计数据变化较小的USB,可以依照情况展开适当天数的内存,第伊瓦诺调阅的时候直接取内存加载,既可以优化USB任务堆栈,更能节省天数和资源。

增建两个Map集合cachMap用作存放USB内存集合,USB展开流程有所改变,如下图。允诺AUSB的时候,先推论与否有同样的允诺存在于堆栈中,如有则中止,不同点在于,如若USB没有中止则推论USB则推论与否有内存且处于有效期内,推论成功则回到缓存,反则堆栈新增USB,允诺完成的时候将结果内存,允诺A移除堆栈。

Axios封装之取消重复请求和接口缓存
/** axiosPCB 允诺截击、积极响应截击 */ import axios from axios; import router from ../router; import store from ../store/index; import qs from qs; const CancelToken = axios.CancelToken, apiCach = { cachMap: new Map() /** 内存列表 */, taskList: [] /** 允诺任务列表 */, /** 新增任务 */ addTask(config, cancelToken) { this.taskList.push({ original: `${config.url}&${config.method}`, cancelToken }); }, /** 删除任务 */ deleteTask(config, start, cancelToken) { let cancel = false; for (let i in this.taskList) { if (this.taskList[i][original] == `${config.url}&${config.method}`) { this.taskList[i].cancelToken(); this.taskList.splice(i, 1); cancel = true; break; } } if (!cancel && start) { this.deleteCach(config, cancelToken); } }, /** 创建key */ createKey(config) { let str = ; config.url && (str += config.url); if (config.method) { str += ,method: + config.method; if (config.method === get) { str += ,data: + qs.stringify(config.params) + ; } else { str += ,data: + config.data; } } return str; }, /** 删除内存 */ deleteCach(config, cancelToken) { let cachMap = this.cachMap; const key = this.createKey(config), now = new Date().getTime(); let cach = cachMap.get(key) || {}; if (cach && cach.expirationTime && now <= cach.deadline && cach.data) { cach.cach = true; cancelToken(cach.data); } }, /** 新增内存 */ addCach(config, cancel) { const key = this.createKey(config), expirationTime = config.headers.expirationTime || 0; if (expirationTime) { this.cachMap.set(key, { expirationTime, deadline: new Date().getTime() + expirationTime, data: , cancel }); } }, /** 更新内存 */ updateCach(res) { if (!res || !res.config) { return false; } const key = this.createKey(res.config), oldVal = this.cachMap.get(key); if (!oldVal) { return false; } this.cachMap.set(key, { expirationTime: oldVal.expirationTime, deadline: oldVal.deadline, data: res }); }, }, /** 创建axios实例 */ instance = axios.create({ timeout: 1000 * 12, }); /** 增设post允诺头 */ instance.defaults.headers.post[Content-Type] = application/x-www-form-urlencoded; /** 允诺圣夫龙*/ instance.interceptors.request.use( (config) => { config.cancelToken = new CancelToken((c) => { /** 删除任务 | 内存 */ apiCach.deleteTask(config, true, c); /** 新增任务 | 内存 */ apiCach.addTask(config, c); apiCach.addCach(config, c); }); config.headers.expirationTime = void 0; let token = window.localStorage.getItem(token); token = token ? token : ; token && (config.headers.Authorization = token); return config; }, (error) => Promise.reject(error) ); /** 积极响应圣夫龙 */ instance.interceptors.response.use( (res) => { apiCach.deleteTask(res.config, false); apiCach.updateCach(res); return Promise.resolve(res); }, // 允诺失利 (error) => { if (error) { let { response } = error; /** 浏览器报错 */ if (response) { if (response.status == 401 || response.status == 403) { localStorage.removeItem(token); store.commit(loginSuccess, null); router.replace(/login); } } if (error.message) { if (typeof error.message === string) { response = { code: 100002, message: error.message }; } else if (typeof error.message === object) { response = error.message; } } else { response = {}; } return Promise.resolve(response ? response : { code: 100002 }); } else { return Promise.resolve({ code: 100002 }); } } ); export default instance;

USB允诺的时候,假如需要内存需要在header里增加expirationTime(ms),标识符如下。

return axios.post(/example, qs.stringify(params), { headers: { expirationTime : 60*1000,//内存一分钟内有效 } });

USB允诺的时候回重定义exprianTime字段为空。

最后我还考虑过,如USB内存天数较长,可以考虑将apiCach里的cachMap内存于localstorage,接着定期更新,这样每天关上网页或者刷新的时候,也可以有效缓解首页加载速率,但是目前工程项目利用率不是很高,因此就没采用。

当然假如我们还有什么好的优化可以留言告诉我哦。

相关文章

发表评论
暂无评论
官方客服团队

为您解决烦忧 - 24小时在线 专业服务