js实现请求重试

1,258 阅读1分钟
const delay = (mileSeconds = 2200) =>{
  return new Promise((resolve) => {
    setTimeout(() => {
      resolve('')
    }, mileSeconds)
  })
}
const recursion = (promiseFun, resolve, reject, count, totalCount) => {
  delay().then(() => {
    promiseFun().then((res) => {
      resolve(res)
    }).catch(err => {
      if(count >= totalCount) {
        reject(err) // 持续调用失败,reject掉
        return
      }
      // 调用失败,但是还没到重试次数,进入重试
      recursion(promiseFun, resolve, reject, count+1, totalCount)
    })
  })
}
export const requestTry = (promiseFun, totalCount = 5) => {
  return new Promise((resolve,reject) => {
    let count = 1
    promiseFun().then(res => {
      resolve(res) // 一次调用成功,直接resolve
    }).catch(err => {
      if(totalCount <= 1) {
        reject(err)// totalCount <= 1的情况下,就直接reject,就算是0,也至少请求1次
        return
      }
      // 一次调用失败,但是还没到总调用次数就进入重试
      recursion(promiseFun, resolve, reject, count +1, totalCount)
    })
  })
}
export default requestTry

delay()是延时函数,不用多说;recursion()是递归调用;requestTry是重试函数并且向外导出,接受2个参数,一个是promiseFun—具体执行接口调用的方法,一个是totalCount—重试次数,默认5次,返回Promise,方便后续操作。

最重要的是promiseFun方法如何写,得到想要的内容就resolve;调用失败,或者返回结果不是想要的,就reject掉,requestTry得到reject,会进入重试,重试次数达到了,不管结果如何,最终也会退出重试。

使用方法

使用vue-admin-template作为原始项目,直接用mock请求来试一下重试机制。dashboard页面增加一个按钮,调用getInfo请求。

import { getInfo } from '@/api/user'
import requestTry from '@/utils/retry'

export default {
  methods: {
    handleClick() {
      requestTry(this.getData).then(res => {
        console.log('res',res)
      }).catche(err => {
        console.log(err)
      })
    },
    getData() { // promiseFun 方法
      return new Promise((resolve,reject) => {
        getInfo('admin-token').then(res => {
          if(res.code === 20000){
            resolve({success: true, data: res})
          }else{
            reject({success: false, data: res})
          }
        }).catch(err => {
          reject({success: false, data: err})
        })
      })
    }
  }
}

requestTry(promiseFun,1),requestTry(promiseFun,0),只会调用一次接口

requestTry(promiseFun,3)最多会调用3次接口,totalCount默认为5。

参考

juejin.cn/post/684490…