/**
|
* axios 封装
|
* 包含请求/响应拦截器、统一错误处理、Loading状态管理
|
*/
|
|
import axios from 'axios';
|
import { message } from 'antd';
|
import config from '../config/env';
|
|
// 创建 axios 实例
|
const service = axios.create({
|
baseURL: config.baseURL,
|
timeout: config.timeout,
|
withCredentials: config.withCredentials
|
});
|
|
// 请求计数器,用于Loading状态控制
|
let requestCount = 0;
|
// let loadingInstance = null; // 预留:全局Loading实例
|
|
// 显示Loading
|
const showLoading = () => {
|
if (requestCount === 0) {
|
// 这里可以集成全局Loading组件
|
// loadingInstance = Loading.service({ fullscreen: true, text: '加载中...' });
|
}
|
requestCount++;
|
};
|
|
// 隐藏Loading
|
const hideLoading = () => {
|
requestCount--;
|
if (requestCount <= 0) {
|
requestCount = 0;
|
// if (loadingInstance) {
|
// loadingInstance.close();
|
// loadingInstance = null;
|
// }
|
}
|
};
|
|
// 请求拦截器
|
service.interceptors.request.use(
|
(config) => {
|
// 显示Loading
|
showLoading();
|
|
// 添加认证token(如果有的话)
|
const token = localStorage.getItem('access_token');
|
if (token) {
|
config.headers.Authorization = `Bearer ${token}`;
|
}
|
|
|
|
// 打印请求日志(开发环境)
|
if (process.env.NODE_ENV === 'development') {
|
console.log('🚀 Request:', {
|
url: config.url,
|
method: config.method,
|
params: config.params,
|
data: config.data
|
});
|
}
|
|
return config;
|
},
|
(error) => {
|
hideLoading();
|
console.error('Request Error:', error);
|
return Promise.reject(error);
|
}
|
);
|
|
// 响应拦截器
|
service.interceptors.response.use(
|
(response) => {
|
hideLoading();
|
|
// 如果是blob类型(文件下载),直接返回完整响应
|
if (response.config.responseType === 'blob') {
|
if (process.env.NODE_ENV === 'development') {
|
console.log('✅ Blob Response:', response);
|
}
|
return response;
|
}
|
|
const res = response.data;
|
|
// 打印响应日志(开发环境)
|
if (process.env.NODE_ENV === 'development') {
|
console.log('✅ Response:', res);
|
}
|
|
// 根据后端约定判断请求是否成功
|
if (res.code !== 200 && res.code !== 201) {
|
// 统一错误处理
|
const errorMsg = res.message || '请求失败';
|
|
// 特殊状态码处理
|
switch (res.code) {
|
case 401:
|
message.error('登录已过期,请重新登录');
|
// 可以跳转到登录页
|
// window.location.href = '/login';
|
break;
|
case 403:
|
message.error('没有权限访问该资源');
|
break;
|
case 404:
|
message.error('请求的资源不存在');
|
break;
|
case 500:
|
message.error('服务器内部错误');
|
break;
|
default:
|
message.error(errorMsg);
|
}
|
|
return Promise.reject(new Error(errorMsg));
|
}
|
|
// 返回成功的数据
|
return res;
|
},
|
(error) => {
|
hideLoading();
|
|
console.error('Response Error:', error);
|
|
// 网络错误处理
|
if (error.code === 'ECONNABORTED') {
|
message.error('请求超时,请稍后重试');
|
} else if (error.message.includes('Network Error')) {
|
message.error('网络连接异常,请检查网络');
|
} else {
|
message.error(error.message || '请求失败');
|
}
|
|
return Promise.reject(error);
|
}
|
);
|
|
// 封装通用请求方法
|
export const request = {
|
// GET 请求
|
get(url, params = {}, config = {}) {
|
return service.get(url, {
|
params,
|
...config
|
});
|
},
|
|
// POST 请求
|
post(url, data = {}, config = {}) {
|
return service.post(url, data, config);
|
},
|
|
// PUT 请求
|
put(url, data = {}, config = {}) {
|
return service.put(url, data, config);
|
},
|
|
// DELETE 请求
|
delete(url, config = {}) {
|
return service.delete(url, config);
|
},
|
|
// PATCH 请求
|
patch(url, data = {}, config = {}) {
|
return service.patch(url, data, config);
|
}
|
};
|
|
// 导出 axios 实例(供特殊场景使用)
|
export default service;
|