0

我对 axios 和拦截器进行了身份验证,但我遇到了用户注销问题。

当 accessToken 失效时,我用 refreshToken 调用 revalidate。什么时候甚至 refreshToken 无效我想注销用户,但我不确定如何停止/清除应用程序中由 useSWR 和 axios fetcher 触发的所有请求。

这样做的最佳做法是什么?

const initAxios = onAuthFinish => {
  axios.interceptors.request.use(
    config => {
      const accessToken = Cookies.get(authKeys.accessToken)
      const tokenType = Cookies.get(authKeys.tokehType)
      if (accessToken) {
        config.headers.Authorization = `${tokenType} ${accessToken}`
      }
      return config
    }
  )

  let isRefreshing = false
  const refreshSubscribers = []

  const subscribeTokenRefresh = (resolve, reject) => {
    refreshSubscribers.push({resolve, reject})
  }

  const onRrefreshed = token => {
    while (refreshSubscribers.length > 0) {
      const {resolve} = refreshSubscribers.pop()
      resolve(token)
    }
  }

  const onExpired = () => {
    while (refreshSubscribers.length > 0) {
      const {reject} = refreshSubscribers.pop()
      reject()
    }
  }

  axios.interceptors.response.use(
    response => response,
    error => {
      const originalRequest = error.config

      if (error.response.status === 403) {
        // refresh token is invalid - WHAT TO DO HERE?
        removeAuthData()
        onAuthFinish()
        return Promise.reject(error)
      }

      if (error.response.status === 401) {
        if (!isRefreshing) {
          isRefreshing = true
          userApi.refreshLogin(Cookies.get(authKeys.refreshToken)).then(res => {
            isRefreshing = false
            if (res && res.data) {
              setAuthData(res.data)
              const newToken = `${Cookies.get(authKeys.tokehType)} ${Cookies.get(authKeys.accessToken)}`
              axios.defaults.headers.common.Authorization = newToken
              onRrefreshed(newToken)
            }
          }).catch(err => {
            isRefreshing = false
            onExpired()
            // this is caused by reject in 403 status if block - WHAT TO DO HERE?
          })
        }

        const retryOrigReq = new Promise((resolve, reject) => {
          subscribeTokenRefresh(token => {
            originalRequest.headers.Authorization = token
            resolve(axios(originalRequest))
          }, () => {
            originalRequest._retry = false
            reject(axios(originalRequest))
          })
        })
        return retryOrigReq
      }

      return Promise.reject(error)
    },
  )
} 

目前,我正在对所有触发的请求调用拒绝onExpired- 但这仍然会缓存所有请求,因此在用户重新登录后仍然有以前的数据。如果我不拒绝该请求,它就会卡在加载中。

我也试过cache.clear()打电话import {cache} from 'swr'

4

1 回答 1

0

似乎最好的解决方案就是清除 cookie 并调用重定向:

    removeAuthData()
    window.location.href = '/login/' 
于 2021-05-05T19:12:37.877 回答