Vue实现禁止反复发送请求

  • 其实实现上一个请求结束前禁止下次请求的方法很多,最常见的其实就是防抖等等,但如果对所有接口都进行这个操作就很繁琐,就算写一个公共的方法也是即此。
  • 既然上面的方法繁琐,那不如从根源解决问题,已知所有的接口都会通过请求拦截器/请求响应器,那么可以从此处做手脚,一次性解决所有问题。

1.最基础的请求基础代码

import axios from 'axios'
import { getItem, removeItem } from '@/utils/token'
import { Message } from 'element-ui'
import router from '@/router'
const request = axios.create({
  baseURL: "/api",
})
// 请求拦截器
request.interceptors.request.use(function (config) {
  config.headers.Authorization = `Bearer ${getItem("token")}`
  return config;
})
// 响应拦截器
request.interceptors.response.use(function (config) {
  const { status, message } = config.data
  if (status == '500') {
    Message.error('登录已过期,请重新登录')
    removeItem('token')
    router.push('/login')
  } else if (status !== '200' && status !== '500') {
    Message.error(message)
  }
  return config
}, error => {
  console.log(error);
  return Message.error(error)
})
export default request

2. 获取这次请求的请求信息,并做重复拦截

let requestList = []
// 请求拦截器
// 同时记录请求地址与请求方式防止拦截错误 
request.interceptors.request.use(function (config) {
  if (requestList.findIndex(x => x.config === `${config.url}&${config.method}`) === -1) {
    requestList .push({ config: `${config.url}&${config.method}` })
  } else {
    return
  }
  config.headers.Authorization = `Bearer ${getItem("token")}`
  return config;
})

3. 请求结束后清除此接口信息

// 响应拦截器
request.interceptors.response.use(function (config) {
  requestList = requestList.filter((x,index)=>x.config !== `${config.config.url}&${config.config.method}`)
  const { status, message } = config.data
  if (status == '500') {
    Message.error('登录已过期,请重新登录')
    removeItem('token')
    router.push('/login')
  } else if (status !== '200' && status !== '500') {
    Message.error(message)
  }
  return config
}, error => {
  console.log(error);
  return Message.error(error)
})
  • 但这样会有个问题,当请求拦截器不return config时会报一个错误出来
TypeError: Cannot read properties of undefined (reading 'cancelToken')
  • 具体解决的话,建议是单独做个判断,当报错信息为上面时,不进行错误提示

4. 完整代码

import axios from 'axios'
import { getItem, removeItem } from '@/utils/token'
import { Message } from 'element-ui'
import router from '@/router'
const request = axios.create({
  baseURL: "/api",
let requestList = []
// 请求拦截器
// 同时记录请求地址与请求方式防止拦截错误 
request.interceptors.request.use(function (config) {
  if (requestList.findIndex(x => x.config === `${config.url}&${config.method}`) === -1) {
    requestList .push({ config: `${config.url}&${config.method}` })
  } else {
    return
  }
  config.headers.Authorization = `Bearer ${getItem("token")}`
  return config;
})
// 响应拦截器
request.interceptors.response.use(function (config) {
  requestList = requestList.filter((x,index)=>x.config !== `${config.config.url}&${config.config.method}`)
  const { status, message } = config.data
  if (status == '500') {
    Message.error('登录已过期,请重新登录')
    removeItem('token')
    router.push('/login')
  } else if (status !== '200' && status !== '500') {
    Message.error(message)
  }
  return config
}, error => {
  console.log(error);
  return Message.error(error)
})
export default request

你可能感兴趣的:(Vue实现禁止反复发送请求)