141 lines
4.0 KiB
TypeScript
141 lines
4.0 KiB
TypeScript
import axios, {AxiosRequestConfig, AxiosResponse} from 'axios';
|
|
import {message} from 'antd';
|
|
|
|
export interface Response<T = any> {
|
|
code: number;
|
|
message: string;
|
|
data: T;
|
|
success: boolean;
|
|
}
|
|
|
|
export interface RequestOptions extends AxiosRequestConfig {
|
|
retryCount?: number;
|
|
retryDelay?: number;
|
|
}
|
|
|
|
// 默认请求配置
|
|
const defaultConfig: Partial<RequestOptions> = {
|
|
retryCount: 3,
|
|
retryDelay: 1000,
|
|
timeout: 30000
|
|
};
|
|
|
|
// 创建请求实例
|
|
const request = axios.create({
|
|
baseURL: '',
|
|
timeout: 30000,
|
|
withCredentials: true,
|
|
headers: {
|
|
'Content-Type': 'application/json'
|
|
}
|
|
});
|
|
|
|
const defaultErrorMessage = '操作失败';
|
|
|
|
// 创建请求配置
|
|
const createRequestConfig = (options?: Partial<RequestOptions>): RequestOptions => {
|
|
return {
|
|
...defaultConfig,
|
|
...options
|
|
};
|
|
};
|
|
|
|
const responseHandler = (response: AxiosResponse<Response<any>>) => {
|
|
const result = response.data;
|
|
if (result.success && result.code === 200) {
|
|
return result.data;
|
|
} else {
|
|
if (result.message != undefined) {
|
|
message.error(result.message || defaultErrorMessage);
|
|
return Promise.reject(response);
|
|
}
|
|
return Promise.reject(response);
|
|
}
|
|
};
|
|
|
|
|
|
const errorHandler = (error: any) => {
|
|
if (!error.response) {
|
|
message.error('网络连接异常,请检查网络');
|
|
return Promise.reject(error);
|
|
}
|
|
|
|
if (axios.isCancel(error)) {
|
|
return Promise.reject(error);
|
|
}
|
|
|
|
const status = error.response.status;
|
|
let errorMessage = '';
|
|
switch (status) {
|
|
case 401:
|
|
errorMessage = '未授权,请重新登录';
|
|
break;
|
|
case 403:
|
|
errorMessage = '拒绝访问';
|
|
break;
|
|
case 404:
|
|
errorMessage = '请求错误,未找到该资源';
|
|
break;
|
|
case 500:
|
|
errorMessage = '服务异常,请稍后再试';
|
|
break;
|
|
default:
|
|
errorMessage = '服务器异常,请稍后再试!';
|
|
}
|
|
message.error(errorMessage);
|
|
return Promise.reject(error);
|
|
};
|
|
|
|
request.interceptors.request.use(
|
|
(config) => {
|
|
const token = localStorage.getItem('token');
|
|
if (token) {
|
|
config.headers.Authorization = `Bearer ${token}`;
|
|
}
|
|
return config;
|
|
},
|
|
(error) => Promise.reject(error)
|
|
);
|
|
|
|
request.interceptors.response.use(responseHandler, errorHandler);
|
|
|
|
const http = {
|
|
get: <T = any>(url: string, config?: RequestOptions) =>
|
|
request.get<any, T>(url, createRequestConfig(config)),
|
|
|
|
post: <T = any>(url: string, data?: any, config?: RequestOptions) =>
|
|
request.post<any, T>(url, data, createRequestConfig(config)),
|
|
|
|
put: <T = any>(url: string, data?: any, config?: RequestOptions) =>
|
|
request.put<any, T>(url, data, createRequestConfig(config)),
|
|
|
|
delete: <T = any>(url: string, config?: RequestOptions) =>
|
|
request.delete<any, T>(url, createRequestConfig(config)),
|
|
|
|
upload: <T = any>(url: string, file: File, config?: RequestOptions) => {
|
|
const formData = new FormData();
|
|
formData.append('file', file);
|
|
return request.post<any, T>(url, formData, createRequestConfig({
|
|
headers: {'Content-Type': 'multipart/form-data'},
|
|
...config
|
|
}));
|
|
},
|
|
|
|
download: (url: string, filename?: string, config?: RequestOptions) =>
|
|
request.get(url, createRequestConfig({
|
|
responseType: 'blob',
|
|
...config
|
|
})).then(response => {
|
|
const blob = new Blob([response.data]);
|
|
const downloadUrl = window.URL.createObjectURL(blob);
|
|
const link = document.createElement('a');
|
|
link.href = downloadUrl;
|
|
link.download = filename || '';
|
|
document.body.appendChild(link);
|
|
link.click();
|
|
document.body.removeChild(link);
|
|
window.URL.revokeObjectURL(downloadUrl);
|
|
})
|
|
};
|
|
|
|
export default http;
|