import type { HookFetchPlugin } from 'hook-fetch'; import { ElMessage } from 'element-plus'; import hookFetch from 'hook-fetch'; import { sseTextDecoderPlugin } from 'hook-fetch/plugins'; import { useUserStore } from '@/stores'; interface BaseResponse { code: number; data?: any; msg: string; rows?: any; total?: number; } export const request = hookFetch.create({ baseURL: import.meta.env.VITE_API_URL, headers: { 'Content-Type': 'application/json', }, plugins: [sseTextDecoderPlugin({ json: true, prefix: 'data:' })], }); // 错误信息翻译映射 const errorMessageMap: Record = { 'Password input error': '密码输入错误', 'User does not exist': '用户不存在', 'User is not exist': '用户不存在', 'Invalid username or password': '用户名或密码错误', 'Account has been locked': '账号已被锁定', 'Account has been disabled': '账号已被禁用', 'Login expired': '登录已过期', 'no basic auth': '未登录', }; // 翻译错误信息 function translateError(msg: string): string { if (!msg) return '请求失败'; // 精确匹配 if (errorMessageMap[msg]) { return errorMessageMap[msg]; } // 部分匹配(处理类似 "Password input error 1 times" 的情况) for (const [key, value] of Object.entries(errorMessageMap)) { if (msg.includes(key)) { // 提取数字(如错误次数) const match = msg.match(/\d+/); if (match) { return `${value} ${match[0]} 次`; } return value; } } // 没有匹配的翻译,返回原始消息 return msg; } function jwtPlugin(): HookFetchPlugin { const userStore = useUserStore(); return { name: 'jwt', beforeRequest: async (config) => { config.headers = new Headers(config.headers); config.headers.set('authorization', `Bearer ${userStore.token}`); config.headers.set('ClientID', import.meta.env.VITE_CLIENT_ID); // 添加租户ID到请求头 if (userStore.userInfo?.tenantId) { config.headers.set('tenant-id', userStore.userInfo.tenantId); } return config; }, afterResponse: async (response) => { const resp = response.response; // 判断 result 是否已被解析为对象(非 Response) const body = (response.result && !(response.result instanceof Response)) ? response.result : (resp?.ok ? await resp.json() : await resp.clone().json()); if (!resp?.ok) { const errorMsg = translateError(body?.msg); if (body?.code === 401) { userStore.logout(); } ElMessage.error(errorMsg || '请求失败'); return Promise.reject(response); } response.result = body; if (body?.code === 200) { // 返回完整的响应对象,包含 code, data, msg // 前端代码需要从 result.data 中提取实际数据 return response; } const errorMsg = translateError(body?.msg); if (body?.code === 403) { return Promise.reject(response); } if (body?.code === 401) { userStore.logout(); ElMessage.error(errorMsg || '登录已过期,请重新登录'); return Promise.reject(response); } ElMessage.error(errorMsg || '请求失败'); return Promise.reject(response); }, }; } request.use(jwtPlugin()); export const post = request.post; export const get = request.get; export const put = request.put; export const del = request.delete; export default request;