一、前言
在 Vue 项目开发中,我们几乎每天都要与后端 API 打交道 ------ 登录、获取数据、提交表单、上传文件......这些都离不开 Ajax(异步请求)。
虽然现代浏览器原生支持 fetch,但大多数 Vue 项目仍然选择使用第三方库,比如 Axios。为什么?它们之间有什么区别?什么时候该用哪个?
本文将带你深入对比 Vue 项目中最常用的两个 Ajax 方案:
✅ Axios (第三方库)
✅ Fetch API(浏览器原生)
从语法、功能、错误处理、拦截器、兼容性等多个维度全面解析,助你做出更合理的技术选型。
二、先看结论:一句话总结
| 库名 | 一句话总结 | 
|---|---|
| Axios | 功能强大、语法简洁、拦截器完善,Vue 项目首选 | 
| Fetch | 原生支持、无需引入、轻量,适合简单请求或现代项目 | 
📌 推荐结论:
- ✅ 大多数 Vue 项目推荐使用 Axios
 - ✅ 轻量级项目或学习用途可尝试 Fetch
 
三、基本语法对比
1. Axios 发送 GET 请求
            
            
              javascript
              
              
            
          
          import axios from 'axios'
axios.get('/api/users')
  .then(response => {
    console.log(response.data)
  })
  .catch(error => {
    console.error('请求失败:', error)
  })
        2. Fetch 发送 GET 请求
            
            
              javascript
              
              
            
          
          fetch('/api/users')
  .then(response => {
    if (!response.ok) {
      throw new Error(`HTTP error! status: ${response.status}`)
    }
    return response.json()
  })
  .then(data => {
    console.log(data)
  })
  .catch(error => {
    console.error('请求失败:', error)
  })
        🔍 第一印象:
- Axios 语法更简洁,
response.data直接拿到数据 - Fetch 需手动判断 
response.ok,并调用.json()解析 
四、核心功能对比表
| 功能特性 | Axios | Fetch | 
|---|---|---|
| ✅ 基于 Promise | ✔️ | ✔️ | 
| ✅ 浏览器兼容性 | IE9+(需 polyfill) | IE 不支持,现代浏览器原生支持 | 
| ✅ 请求/响应拦截器 | ✔️ 支持,可统一处理 token、loading | ❌ 不支持,需手动封装 | 
| ✅ 自动转换 JSON 数据 | ✔️ 默认解析 response.data | 
❌ 需手动调用 .json() | 
| ✅ 错误处理更友好 | ✔️ 网络错误、HTTP 错误统一抛出 | ❌ HTTP 404/500 不触发 catch,需手动判断 | 
| ✅ 超时设置 | ✔️ timeout: 5000 | 
❌ 原生不支持,需用 AbortController | 
| ✅ 取消请求 | ✔️ 使用 CancelToken 或 AbortController | 
✔️ 使用 AbortController | 
| ✅ 上传进度监听 | ✔️ 支持 onUploadProgress | 
❌ 不支持 | 
| ✅ 下载进度监听 | ✔️ 支持 onDownloadProgress | 
❌ 不支持 | 
| ✅ 默认携带 Cookie | ❌ 需设置 withCredentials: true | 
❌ 需设置 credentials: 'include' | 
💡 Axios 在功能丰富性和开发体验上明显胜出。
五、实战代码示例
✅ 场景 1:POST 提交数据(Axios)
            
            
              javascript
              
              
            
          
          axios.post('/api/login', {
  username: 'admin',
  password: '123456'
}, {
  headers: {
    'Content-Type': 'application/json'
  },
  withCredentials: true // 携带 Cookie
})
.then(res => {
  console.log('登录成功', res.data)
})
        ✅ 场景 1:POST 提交数据(Fetch)
            
            
              javascript
              
              
            
          
          fetch('/api/login', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json'
  },
  body: JSON.stringify({
    username: 'admin',
    password: '123456'
  }),
  credentials: 'include' // 携带 Cookie
})
.then(res => {
  if (!res.ok) throw new Error('登录失败')
  return res.json()
})
.then(data => {
  console.log('登录成功', data)
})
        ✅ 场景 2:请求拦截器(Axios 独有)
            
            
              javascript
              
              
            
          
          // 添加请求拦截器
axios.interceptors.request.use(config => {
  // 每次请求前添加 token
  const token = localStorage.getItem('token')
  if (token) {
    config.headers.Authorization = `Bearer ${token}`
  }
  // 显示 loading
  showLoading()
  return config
})
// 添加响应拦截器
axios.interceptors.response.use(
  response => {
    hideLoading()
    return response
  },
  error => {
    hideLoading()
    if (error.response?.status === 401) {
      alert('登录已过期,请重新登录')
      router.push('/login')
    }
    return Promise.reject(error)
  }
)
        📌 这是 Axios 最大的优势之一:可以全局统一处理认证、错误、loading 状态。
六、在 Vue 项目中如何选择?
推荐使用 Axios 的场景 ✅
| 场景 | 说明 | 
|---|---|
| 中大型项目 | 需要统一管理请求、错误、token | 
| 需要上传/下载进度 | Axios 原生支持 | 
| 需要兼容老浏览器 | Axios + polyfill 支持 IE9+ | 
| 团队协作项目 | 拦截器 + 封装更规范 | 
可以考虑 Fetch 的场景 ⚠️
| 场景 | 说明 | 
|---|---|
| 轻量级项目 | 无需引入额外依赖 | 
| 学习用途 | 理解原生 API 更好 | 
| 现代浏览器环境 | 如 Electron、内部管理系统 | 
| 已使用其他请求库 | 如 ky、swrv 等封装库 | 
七、如何在 Vue 项目中安装和使用 Axios?
1. 安装 Axios
            
            
              bash
              
              
            
          
          npm install axios
        2. 封装请求模块(推荐)
            
            
              javascript
              
              
            
          
          // utils/request.js
import axios from 'axios'
const request = axios.create({
  baseURL: 'https://api.example.com',
  timeout: 10000
})
// 请求拦截器
request.interceptors.request.use(config => {
  const token = localStorage.getItem('token')
  if (token) {
    config.headers.Authorization = `Bearer ${token}`
  }
  return config
})
// 响应拦截器
request.interceptors.response.use(
  response => response.data,
  error => {
    return Promise.reject(error)
  }
)
export default request
        3. 在组件中使用
            
            
              javascript
              
              
            
          
          import request from '@/utils/request'
export default {
  async created() {
    try {
      const data = await request.get('/users')
      this.users = data
    } catch (error) {
      console.error('请求失败:', error)
    }
  }
}
        八、Fetch 的现代替代方案
如果你喜欢 Fetch 的原生感,但又想要更好的开发体验,可以考虑以下封装库:
| 库名 | 特点 | 
|---|---|
ky | 
基于 Fetch 的轻量级封装,API 更友好 | 
swrv | 
带缓存的 Fetch,适合数据频繁请求场景 | 
axios | 
老牌王者,功能全面 | 
九、常见问题解答
❓ 问题 1:Fetch 为什么 HTTP 错误不进 catch?
因为 fetch 只在网络错误时 reject,HTTP 状态码 4xx/5xx 仍属于"成功响应",需手动判断:
            
            
              javascript
              
              
            
          
          if (!response.ok) {
  throw new Error(`HTTP ${response.status}`)
}
        ❓ 问题 2:Axios 会增加打包体积吗?
会,但很小(约 15KB gzip),功能带来的便利远大于体积成本。
❓ 问题 3:Vue 3 中推荐用哪个?
官方不强制,但社区普遍使用 Axios,尤其在企业项目中。
十、总结
| 对比项 | Axios | Fetch | 
|---|---|---|
| 学习成本 | 低,API 简洁 | 中,需处理更多细节 | 
| 功能丰富度 | 高(拦截器、进度、超时) | 低(原生功能有限) | 
| 错误处理 | 友好,自动抛出 | 需手动判断 response.ok | 
| 兼容性 | IE9+(需 polyfill) | 不支持 IE | 
| 是否推荐 | ✅ 强烈推荐 | ⚠️ 仅限轻量或学习 | 
十一、结语
感谢您的阅读!如果你有任何疑问或想要分享的经验,请在评论区留言交流!