request-simple.ts 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115
  1. /**
  2. * 简化版request - 用于测试401跳转
  3. * 如果标准版本不工作,可以临时替换使用这个版本
  4. */
  5. import axios from 'axios'
  6. import type { InternalAxiosRequestConfig, AxiosResponse } from 'axios'
  7. import { ElMessage } from 'element-plus'
  8. import { getToken, getRefreshToken, setToken as saveToken } from '@/utils/auth'
  9. // 获取基础 URL
  10. const getBaseURL = () => {
  11. let url = import.meta.env.VITE_API_BASE_URL || 'http://localhost:8000'
  12. if (url.includes('localhost') && typeof window !== 'undefined' && window.location.hostname !== 'localhost' && window.location.hostname !== '127.0.0.1') {
  13. url = url.replace('localhost', window.location.hostname)
  14. }
  15. return url
  16. }
  17. // 创建axios实例
  18. const request = axios.create({
  19. baseURL: getBaseURL(),
  20. timeout: 30000,
  21. headers: {
  22. 'Content-Type': 'application/json'
  23. }
  24. })
  25. // 请求拦截器
  26. request.interceptors.request.use(
  27. (config: InternalAxiosRequestConfig) => {
  28. const token = getToken()
  29. if (token && config.headers) {
  30. config.headers.Authorization = `Bearer ${token}`
  31. }
  32. return config
  33. },
  34. (error) => {
  35. return Promise.reject(error)
  36. }
  37. )
  38. // 响应拦截器 - 简化版
  39. request.interceptors.response.use(
  40. (response: AxiosResponse) => {
  41. // Token自动更新
  42. const newToken = response.headers['x-new-token']
  43. if (newToken) {
  44. const refreshToken = getRefreshToken()
  45. saveToken(newToken, refreshToken || undefined)
  46. console.log('[简化版] Token已自动刷新')
  47. }
  48. const { code, message } = response.data ?? {}
  49. if ((code === '000000' || code === 0) || code === 200 || typeof code === 'undefined') {
  50. return response.data
  51. }
  52. const errorMsg = message || '请求失败'
  53. if (!response.config.headers?.['Skip-Error-Message']) {
  54. ElMessage.error(errorMsg)
  55. }
  56. const businessError = new Error(errorMsg)
  57. // @ts-ignore
  58. businessError.code = code
  59. // @ts-ignore
  60. businessError.isBusinessError = true
  61. return Promise.reject(businessError)
  62. },
  63. (error) => {
  64. console.log('[简化版] 拦截器捕获错误:', error.response?.status)
  65. // 401错误 - 最简单的处理
  66. if (error.response?.status === 401) {
  67. console.log('[简化版] 检测到401,立即跳转')
  68. // 清除所有认证信息
  69. localStorage.clear()
  70. sessionStorage.clear()
  71. // 显示提示
  72. ElMessage.error('登录已过期,请重新登录')
  73. // 立即跳转
  74. window.location.href = '/login'
  75. // 阻止后续执行
  76. return new Promise(() => {})
  77. }
  78. // 其他错误
  79. const skipErrorMessage = error.config?.headers?.['Skip-Error-Message']
  80. if (error.response) {
  81. const { status, data } = error.response
  82. if (!skipErrorMessage) {
  83. if (status === 403) {
  84. ElMessage.error('权限不足')
  85. } else if (status === 404) {
  86. ElMessage.error('请求的资源不存在')
  87. } else if (status === 500) {
  88. ElMessage.error('服务器内部错误')
  89. } else {
  90. ElMessage.error(data?.message || '请求失败')
  91. }
  92. }
  93. } else {
  94. if (!skipErrorMessage) {
  95. ElMessage.error('网络连接失败')
  96. }
  97. }
  98. return Promise.reject(error)
  99. }
  100. )
  101. export default request