Axios异步并发(多个不同接口/同个接口频繁点击)导致数据覆盖的解决方法:取消重复请求,只保留最后一次请求

前端开发过程中通常使用同步方法(loading)来防止此类问题,但架不住产品经理要求交互友好,拒绝遮罩,必须使用异步,以同一个接口频繁请求为例(频繁点击table不同行,触发行点击事件请求接口):假如触发了两次,第一次接口5s返回数据①,第二次1s返回数据②,那么先获取到②赋值到页面,这时①数据接收到了,会覆盖②的数据。

        axios中可以使用拦截器统一处理。本文提供的思路就是利用 axios interceptors API 拦截请求,检测是否有多个相同的请求同时处于 pending 状态,如果有就调用 cancel token API 取消重复的请求,只保留最后一次请求。

        直接上代码:

        1、在axios中声明数组记录标识

let pending = []; //声明一个数组用于存储每个请求的标识
let cancelToken = axios.CancelToken;
let removePending = (config) => {
  //查找数组中是否存在相同请求,存在则取消
  for(let p in pending){ 
    if(pending[p].u === config.url.split('?')[0] + '&' + config.method) {
      pending[p].f(); //执行取消操作
      pending.splice(p, 1); //数组移除当前请求
    }
  }
}

        2、在请求前校验拦截

service.interceptors.request.use(config => {
    removePending(config); //在一个axios发送前执行校验取消操作
    config.cancelToken = new cancelToken((c)=>{// pending存放每一次请求的标识,config.url请求路径,config.params参数,config.method请求方法
    pending.push({ u: config.url.split('?')[0] +'&' + config.method, f: c});
  });

    return config;
}, error => {
    pending = [];//清空记录——这里出现错误可能是网络波动造成的,清空 pending 对象
    return Promise.reject(error);
})

        3、在请求返回后维护 pending 

service.interceptors.response.use(
  response => {
      // 清除当前记录
      for(let p in pending){
        if(pending[p].u === response.config.url.split('?')[0] + '&' + response.config.method) {
          pending.splice(p, 1);
        }
      }
      return response.data  
  },
  error => {
      pending = [];//清空记录
      return Promise.reject(error)
  }
)

Axios拦截器的工作原理请参考官方文档axios中文文档|axios中文网http://www.axios-js.com/zh-cn/docs/

  • 16
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值