Vue3 + Axios 二次封装与统一错误处理实践
在前后端分离项目中,如果在每个组件里都直接写 `axios.get()`,代码会变得非常冗余且难以维护。这是我在项目中使用的 Axios 封装方案。
1. 封装目标
- 统一配置: BaseURL、超时时间。
- 请求拦截: 自动携带 Token,防止 CSRF。
- 响应拦截: 统一处理 HTTP 状态码(401跳转登录,500提示报错)。
- 全局 Loading: 请求发起时显示加载动画,结束时隐藏。
2. 核心代码实现 (request.js)
import axios from 'axios'
import { ElMessage } from 'element-plus'
import router from '@/router'
// 创建实例
const service = axios.create({
baseURL: import.meta.env.VITE_API_URL, // 从环境变量读取
timeout: 5000
})
// 请求拦截器
service.interceptors.request.use(
config => {
// 如果有 Token,自动携带
const token = localStorage.getItem('token')
if (token) {
config.headers['Authorization'] = 'Bearer ' + token
}
return config
},
error => {
return Promise.reject(error)
}
)
// 响应拦截器
service.interceptors.response.use(
response => {
const res = response.data
// 假设后端约定 code !== 200 为业务错误
if (res.code !== 200) {
ElMessage.error(res.message || 'Error')
return Promise.reject(new Error(res.message || 'Error'))
} else {
return res
}
},
error => {
console.log('err' + error)
// 统一处理 HTTP 状态码
if (error.response && error.response.status === 401) {
ElMessage.error('登录过期,请重新登录')
router.push('/login')
} else {
ElMessage.error(error.message)
}
return Promise.reject(error)
}
)
export default service
3. 总结
通过这层封装,我在组件里调用接口变得非常清爽:
// api/user.js
export function login(data) {
return request({
url: '/user/login',
method: 'post',
data
})
}