0Pricing
Vue Academy · 课时

使用 Axios 拦截器调用需认证的 API

为 Authorization 请求头配置请求拦截器,以及处理 401 → 刷新 → 重试的响应拦截器

使用 Axios 拦截器调用需认证的 API 是 CoddyKit 上的免费 Vue Academy 课时。 这是第 3 节课,共 4 节。 你可以在下方免费阅读本课时的完整内容 — 然后在浏览器中使用内置代码编辑器和全天候 AI 导师进行实践。 这是 Vue Academy 学习路径的一部分,你的进度在网页和 CoddyKit 应用中同步。 Vue Academy 课程共包含 4 节课。

拦截器模式

与其在每次调用中都附加身份验证请求头并处理 401,不如使用 Axios 拦截器集中处理这些逻辑。请求拦截器负责添加 token,响应拦截器则透明地处理过期和刷新。

创建 Axios 实例

创建一个专用实例,配置 API 基础 URL 和 withCredentials,这样 httpOnly 刷新 Cookie 就会被发送到刷新端点。

import axios from 'axios'

const api = axios.create({
  baseURL: '/api',
  withCredentials: true // send cookies
})

export default api

在内存中存储访问 token

将访问 token 保存在模块变量(或 Pinia 存储)中,而不是 localStorage 中。一对简短的访问器可以让拦截器读取和更新它。

let accessToken = null

export function setAccessToken(t) { accessToken = t }
export function getAccessToken() { return accessToken }

请求拦截器:添加请求头

请求拦截器会在每次请求前运行,并在 token 存在时附加 Authorization: Bearer <token>。

api.interceptors.request.use((config) => {
  const token = getAccessToken()
  if (token) {
    config.headers.Authorization = 'Bearer ' + token
  }
  return config
})

响应拦截器:捕获 401

响应拦截器会原样传递成功响应,但遇到 401 时会触发刷新流程。

api.interceptors.response.use(
  (response) => response,
  async (error) => {
    const original = error.config
    if (error.response?.status === 401 && !original._retried) {
      // ... refresh and retry (next scenes)
    }
    return Promise.reject(error)
  }
)

防止无限重试循环

使用类似 _retried 的标记标记失败的请求,使其只重试一次。如果刷新操作本身返回 401,请求会被拒绝,而不是永远循环。

if (error.response?.status === 401 && !original._retried) {
  original._retried = true
  // attempt refresh exactly once for this request
}

调用刷新端点

遇到 401 时,向 /auth/refresh 发送 POST 请求。浏览器会自动发送 httpOnly 刷新 Cookie,服务器则返回新的访问 token。

const { data } = await api.post('/auth/refresh')
setAccessToken(data.accessToken)

重试原始请求

刷新完成后,更新原始配置中的请求头并重新执行请求。用户完全不会察觉到这次中断。

original.headers.Authorization = 'Bearer ' + data.accessToken
return api(original) // retry the original request

处理并发的 401 响应

如果许多请求同时失败,您不会希望发起 N 个并行的刷新请求。请共享一个正在执行的刷新承诺,让排队的请求等待它完成,然后使用新的 token 重试。

let refreshing = null

function refreshOnce() {
  if (!refreshing) {
    refreshing = api.post('/auth/refresh')
      .finally(() => { refreshing = null })
  }
  return refreshing
}

放弃操作:强制退出登录

如果刷新失败(刷新 token 已过期或无效),请清除内存中的 token 并重定向到登录页面。这是整个应用统一处理会话过期的唯一位置。

try {
  await refreshOnce()
} catch {
  setAccessToken(null)
  router.push('/login')
  return Promise.reject(error)
}

在组件中使用实例

组件只需导入配置好的 api 实例并发起调用。身份验证请求头、刷新和重试对组件代码完全透明。

<script setup>
import api from '@/lib/api'
import { ref, onMounted } from 'vue'

const profile = ref(null)
onMounted(async () => {
  const { data } = await api.get('/me')
  profile.value = data
})
</script>

快速检查

测试您对 Axios 拦截器的理解。

回顾

您已经学会了如何使用拦截器发起经过身份验证的调用:

  • 请求拦截器从内存中的 token 添加 Authorization: Bearer
  • 响应拦截器捕获 401 并执行刷新
  • _retried 标记确保原始请求恰好重试一次
  • POST /auth/refresh 使用 httpOnly Cookie 获取新的 token
  • 并发出现 401 时共享一个刷新承诺;失败时强制退出登录

常见问题解答

「使用 Axios 拦截器调用需认证的 API」课时是免费的吗?

是的 — 「使用 Axios 拦截器调用需认证的 API」的完整文本可在网页上免费阅读。要进行交互式练习(内置代码编辑器和全天候 AI 导师)并解锁 Vue Academy 课程的其余内容,请升级到 CoddyKit PRO。 Vue Academy 课程共包含 4 节课。

「使用 Axios 拦截器调用需认证的 API」这节课中我会学到什么?

为 Authorization 请求头配置请求拦截器,以及处理 401 → 刷新 → 重试的响应拦截器 你通过在浏览器中直接运行的动手代码来练习 Vue Academy,全天候 AI 导师会在你学习这节课的过程中回答你的问题。

学习 Vue Academy 需要有经验吗?

无需任何先前经验。CoddyKit 上的 Vue Academy 课程适合初学者到高级学习者,你可以从这里开始或从头开始,按照自己的节奏学习。 这是第 3 节课,共 4 节。

「使用 Axios 拦截器调用需认证的 API」课时需要多长时间?

大多数 CoddyKit 课程大约需要 5–10 分钟。每节课都很精短且互动,所以你能稳步进步,并在网页和应用中从离开的地方继续。

我能在这节 Vue Academy 课中编写并运行代码吗?

能。每节 Vue Academy 课都包含内置代码编辑器,你可以在浏览器中直接编写并运行真实代码,并获得即时 AI 反馈 — 无需本地设置。

此课程中的所有课时

  1. 面向 Vue SPA 的 Fastify 后端
  2. JWT 认证:登录与刷新
  3. 使用 Axios 拦截器调用需认证的 API
  4. 将全栈 Vue 应用部署到生产环境
← 返回 Vue Academy