Duplicate request cancellation commonly used by vue axios interceptors

  • 2021-11-14 04:40:01
  • OfStack

Introduction

The previous article introduced the simple encapsulation of axios, and knew the application scenarios and methods of axios interceptor. Today, let's look at how the interceptor handles the situation that the response time is too long and the number of requests is too high.

How to cancel the request

Axios uses the internally supplied CancelToken to cancel the request

Official website example 1: Create cancel token with CancelToken. source factory method, like this


const CancelToken = axios.CancelToken;
const source = CancelToken.source();

axios.get('/user/12345', {
  cancelToken: source.token
}).catch(function(thrown) {
  if (axios.isCancel(thrown)) {
    console.log('Request canceled', thrown.message);
  } else {
     //  Handling errors 
  }
});

axios.post('/user/12345', {
  name: 'new name'
}, {
  cancelToken: source.token
})

//  Cancel the request ( message  Parameter is optional) 
source.cancel('Operation canceled by the user.');

Official website example 2: Create cancel token by passing an executor function to the constructor of CancelToken:


const CancelToken = axios.CancelToken;
let cancel;

axios.get('/user/12345', {
  cancelToken: new CancelToken(function executor(c) {
    // executor  Function reception 1 A  cancel  Function as an argument 
    cancel = c;
  })
});

// cancel the request
cancel();

You can see that all of the above cancel token are created in a single request. In actual work, we need to process all the requests. Next, let's look at how to cancel the request in the interceptor

Cancel duplicate request in interceptor


import axios from 'axios'
import baseURL from './config'
import qs from 'qs'

const pendingRequest = new Map(); //  Request object 
const CancelToken = axios.CancelToken;

axios.defaults.timeout = 30000
axios.defaults.baseURL = baseURL.target

//  Add a request interceptor 
axios.interceptors.request.use(function(config) {
  //  What to do before sending the request 
  config.headers = {
      'content-type': 'application/json',
      'token': getToken()
  }
  //  Acquisition request key
  let requestKey = getReqKey(config);

  //  Determining whether it is a duplicate request 
  if (pendingRequest.has(requestKey)) { //  Is a duplicate request 
    removeReqKey(requestKey); //  Cancel 
  }else{
    //  Settings cancelToken
    config.cancelToken = new CancelToken(function executor(cancel) {
      pendingRequest.set(requestKey, cancel); //  Settings 
    })
  }

  return config;
}, function (error) {
  //  Request error 
  return Promise.reject(error);
});

//  Add a response interceptor 
axios.interceptors.response.use(function (response) {
  //  Delete from the request object requestKey
  let requestKey = getReqKey(response.config);
  removeReqKey(requestKey);

  //  Do something about the returned data   For example, state interception 
  if (response.data.status !== 200) {
      Toast({
        message: response.data.message,
        type: 'warning',
        duration: 1000
      })
      return
    }
    
  //  No problem   Return server data 
  return response.data;
}, function (error) {
  let requestKey = getReqKey(error.config);
  removeReqKey(requestKey);
  
  //  Response error 
  return Promise.reject(error);
});

//  Acquisition request key
function getReqKey(config) {
  //  Request mode, request address and string generated by request parameters are used as the basis for whether the request is repeated or not 
  const { method, url, params, data } = config; //  Deconstruct these parameters 
  // GET ---> params  POST ---> data
  const requestKey =  [ method, url, qs.stringify(params), qs.stringify(data)].join('&');
  return requestKey;
}

//  Cancel duplicate request 
function removeReqKey(key) {
  const cancelToken = pendingRequest.get(key);
  cancelToken(key); //  Cancel a previously sent request 
  pendingRequest.delete(key); //  Delete from the request object requestKey
}

Conclusion

The above is the processing of repeated requests. If you don't know the interceptor, you can see the previous article. If you have any questions, you are welcome to correct them. I will update them in the first time.


Related articles: