import { merge } from "lodash"; import configs from "@/config"; import { Axios } from "./axios"; import { ContentTypeEnum, RequestCodeEnum, RequestMethodsEnum, } from "@/enums/requestEnums"; import type { AxiosHooks } from "./type"; import { clearAuthInfo, getToken } from "../auth"; import feedback from "../feedback"; import NProgress from "nprogress"; import { AxiosError, type AxiosRequestConfig } from "axios"; import router from "@/router"; import { PageEnum } from "@/enums/pageEnum"; // 处理axios的钩子函数 const axiosHooks: AxiosHooks = { requestInterceptorsHook(config) { NProgress.start(); const { withToken, isParamsToData } = config.requestOptions; const params = config.params || {}; const headers = config.headers || {}; // 添加token if (withToken) { const token = getToken(); headers.token = token; } // POST请求下如果无data,则将params视为data if ( isParamsToData && !Reflect.has(config, "data") && config.method?.toUpperCase() === RequestMethodsEnum.POST ) { config.data = params; config.params = {}; } config.headers = headers; return config; }, requestInterceptorsCatchHook(err) { NProgress.done(); return err; }, async responseInterceptorsHook(response) { NProgress.done(); const { isTransformResponse, isReturnDefaultResponse } = response.config.requestOptions; //返回默认响应,当需要获取响应头及其他数据时可使用 if (isReturnDefaultResponse) { return response; } // 是否需要对数据进行处理 if (!isTransformResponse) { return response.data; } const { code, data, show, msg } = response.data; switch (code) { case RequestCodeEnum.SUCCESS: if (show) { msg && feedback.msgSuccess(msg); } return data; case RequestCodeEnum.FAIL: if (show) { msg && feedback.msgError(msg); } return Promise.reject(data); case RequestCodeEnum.SERVER_ERROR: if (show) { msg && feedback.msgError(msg); } return Promise.reject(data); case RequestCodeEnum.LOGIN_FAILURE: clearAuthInfo(); router.push(PageEnum.LOGIN); return Promise.reject(); case RequestCodeEnum.OPEN_NEW_PAGE: window.location.href = data.url; return data; default: return data; } }, responseInterceptorsCatchHook(error) { NProgress.done(); if (error.code !== AxiosError.ERR_CANCELED) { error.message && feedback.msgError(error.message); } return Promise.reject(error); }, }; const defaultOptions: AxiosRequestConfig = { //接口超时时间 timeout: configs.timeout, // 基础接口地址 baseURL: configs.baseUrl, //请求头 headers: { "Content-Type": ContentTypeEnum.JSON, version: configs.version }, // 处理 axios的钩子函数 axiosHooks: axiosHooks, // 每个接口可以单独配置 requestOptions: { // 是否将params视为data参数,仅限post请求 isParamsToData: true, //是否返回默认的响应 isReturnDefaultResponse: false, // 需要对返回数据进行处理 isTransformResponse: true, // 接口拼接地址 urlPrefix: configs.urlPrefix, // 忽略重复请求 ignoreCancelToken: false, // 是否携带token withToken: true, // 开启请求超时重新发起请求请求机制 isOpenRetry: true, // 重新请求次数 retryCount: 2, }, }; function createAxios(opt?: Partial<AxiosRequestConfig>) { return new Axios( // 深度合并 merge(defaultOptions, opt || {}) ); } const request = createAxios(); export default request;