只对url和方法进行比较:

import axios from 'axios'
import { Message } from 'element-ui'
import route from '@/router'

const duration = 2 * 1000
let preDate = 0

const Cancel = axios.CancelToken
let httpPending = []

function removeHttpPending(config) {
  // console.log(config)
  httpPending.map((item, index, arr) => {
    // console.log(item)
    if (item.u === config.url + '&' + config.method) {
      console.log(`${config.url}: 短时间内重复请求`)
      item.f()
      arr.splice(index, 1)
    }
    return config
  })
}

function clearHttpPending() {
  httpPending = []
}

// create an axios instance
const service = axios.create({
  baseURL: process.env.VUE_APP_BASE_API, // url = base url + request url
  withCredentials: true, // send cookies when cross-domain requests
  headers: { 'From': 'browser' },
  timeout: 30000 // request timeout
})

// 当有重复请求的时候,就删除前一个请求
service.interceptors.request.use((config) => {
  removeHttpPending(config)
  config.cancelToken = new Cancel(c => {
    httpPending.push({ u: config.url + '&' + config.method, f: c })
  })

  return config
}, (err) => {
  return Promise.reject(err)
})

// response interceptor
service.interceptors.response.use(
  /**
   * If you want to get http information such as headers or status
   * Please return  response => response
  */

  /**
   * Determine the request status by custom code
   * Here is just an example
   * You can also judge the status by HTTP Status Code
   */
  response => {
    clearHttpPending()
    const res = response.data
    // if the custom code is not 20000, it is judged as an error.
    if (!res.success) {
      Message({
        message: res.message || 'Error',
        type: 'error',
        duration: duration
      })
      return Promise.reject(new Error(res.message || 'Error'))
    } else {
      return res
    }
  },
  error => {
    const date = new Date().getTime()
    if ((date - preDate) > 2000) {
      preDate = date
      console.log('err' + error) // for debug
      if (error.response.status === 401) {
        route.push('/login')
      } else {
        Message({
          message: error.response.data.message,
          type: 'error',
          duration: duration
        })
      }
    }
    return Promise.reject(error)
  }
)

export default service

加上对参数的校验:

function removeHttpPending(config) {

  httpPending.map((item, index, arr) => {

    if (item.u === config.url + '&' + config.method) {
      if (!(item.data && isSameKeyValueObj(item.data, config.data)) && !(item.params && isSameKeyValueObj(item.params, config.params))) {
        return config
      }
      console.warn(`${config.url}: 短时间内重复请求`)
      item.f()
      arr.splice(index, 1)
    }
    return config
  })
}

function isObj(obj) {
  const str = Object.prototype.toString.call(obj)
  if (str === '[object Object]' || str === '[object Array]') {
    return true
  }
  return false
}

function isSameKeyValueObj(target, source) {
  if (!isObj(target) || !isObj(source)) {
    return false
  }
  const targetkeys = Object.getOwnPropertyNames(target)
  const sourcekeys = Object.getOwnPropertyNames(source)
  if (targetkeys.length !== sourcekeys.length) {
    return false
  }
  for (let i = 0; i < targetkeys.length; i++) {
    const key = targetkeys[i]
    if (!isObj(target[key]) && target[key] !== source[key]) {
      return false
    }
    if (isObj(target[key])) {
      return isSameObj(target[key], source[key])
    }
  }
  return true
}




http.interceptors.request.use((config) => {
  removeHttpPending(config)
  config.cancelToken = new Cancel(c => {

    httpPending.push({
      u: config.url + '&' + config.method,
      f: c,
      data: config.data,
      params: config.params
    })
  })
  return config
}, (err) => {
  return Promise.reject(err)
})