app.tsx 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190
  1. import { queryCurrentUser, queryPermData } from './services/user'
  2. import { history } from 'umi'
  3. import RightContent from '@/components/RightContent'
  4. import { message, notification } from 'antd'
  5. import logo from '../public/logo.svg'
  6. import { getToken } from '@/utils/auth'
  7. import { tryChangeWorkStatus } from './components/RightContent/Book'
  8. import { getAuthCache, setAuthCache } from './utils/auth'
  9. import { LAYOUT_COLLAPSED_KEY } from './utils/cache/cacheEnum'
  10. import consts from './consts'
  11. import ModalStore from './components/Modal1'
  12. const loginPath = '/user/login'
  13. // 重新构建MenuData,解决重定向没有权限的路由
  14. // const generateMenu = (menuData, permission) => menuData.map(menu => {
  15. // })
  16. export async function getInitialState() {
  17. // 如果是登录页面,不执行
  18. const fetchUserInfo = async () => {
  19. try {
  20. const res = await queryCurrentUser()
  21. return res.data
  22. } catch (error) {
  23. history.push(loginPath)
  24. }
  25. return undefined
  26. }
  27. const fetchPermData = async () => {
  28. try {
  29. const res = await queryPermData()
  30. return res.data
  31. } catch (error) {
  32. message.error('获取数据权限失败,请联系管理员')
  33. }
  34. return {}
  35. }
  36. // 如果是登录页面,不执行
  37. if (history.location.pathname !== loginPath) {
  38. const userInfo = (await fetchUserInfo()) || {}
  39. const permData = (await fetchPermData()) || {}
  40. // if (userInfo?.currentUser?.staffId) {
  41. // const { username, staffId: id, wsToken: token } = userInfo?.currentUser
  42. // ws.init(`ws://cld2qa.com/summon/v1/chat/link?username=${username}&id=${id}&token=${token}`, {
  43. // onMessage
  44. // })
  45. // }
  46. const collapsed = getAuthCache(LAYOUT_COLLAPSED_KEY) || false
  47. return {
  48. fetchUserInfo,
  49. fetchPermData,
  50. permData,
  51. ...userInfo,
  52. settings: { collapsed, defaultCollapsed: collapsed }
  53. }
  54. }
  55. return {
  56. fetchUserInfo,
  57. fetchPermData,
  58. settings: {}
  59. }
  60. }
  61. export const layout = ({ initialState, setInitialState }) => {
  62. const onCollapse = collapsed => {
  63. setInitialState({ ...initialState, settings: { ...initialState.settings, collapsed } })
  64. setAuthCache(LAYOUT_COLLAPSED_KEY, collapsed)
  65. }
  66. return {
  67. logo,
  68. // menu: {
  69. // params: {
  70. // userId: initialState?.currentUser?.staffId
  71. // },
  72. // request: (_, defaultMenuData) => {
  73. // console.log('defaultMenuData', defaultMenuData)
  74. // return defaultMenuData
  75. // }
  76. // },
  77. rightContentRender: () => <RightContent />,
  78. disableContentMargin: false,
  79. waterMarkProps: {
  80. content: initialState?.currentUser?.username
  81. },
  82. onPageChange: async location => {
  83. // 如果没有登录,重定向到 login
  84. if (!initialState?.currentUser?.staffId && location.pathname !== loginPath) {
  85. history.replace('/user/login')
  86. } else {
  87. location.pathname !== loginPath &&
  88. tryChangeWorkStatus(initialState?.currentUser?.staffId, location.pathname)
  89. }
  90. // if (
  91. // initialState?.currentUser?.staffId &&
  92. // location.pathname !== loginPath &&
  93. // PERMISSION_NEED_PATH.includes(location.pathname) &&
  94. // !initialState?.permData
  95. // ) {
  96. // const permData = await initialState.fetchPermData()
  97. // permData && setInitialState({ ...initialState, permData })
  98. // }
  99. },
  100. childrenRender: children => <ModalStore>{children}</ModalStore>,
  101. // links: [
  102. // <div className="ant-menu-title-content">
  103. // <AddressBook theme="outline" className="anticon" />
  104. // <span className="ant-pro-menu-item-title">通讯录</span>
  105. // </div>
  106. // ],
  107. // menuHeaderRender: false,
  108. ...initialState?.settings,
  109. breakpoint: false,
  110. onCollapse
  111. }
  112. }
  113. const errorHandler = error => {
  114. const { response } = error
  115. if (response && response.status) {
  116. const errorText = codeMessage[response.status] || response.statusText
  117. const { status, url } = response
  118. notification.error({
  119. message: `请求错误 ${status}: ${url}`,
  120. description: errorText
  121. })
  122. } else if (!response) {
  123. notification.error({
  124. description: '您的网络发生异常,无法连接服务器',
  125. message: '网络异常'
  126. })
  127. }
  128. return response
  129. }
  130. const authHeaderInterceptor = (url, options) => {
  131. const token = getToken()
  132. if (token) {
  133. // 在白名单里的请求放过
  134. if (consts.TOKEN_WHITE_LIST.includes(url)) {
  135. return { url, options }
  136. }
  137. // eslint-disable-next-line no-param-reassign
  138. options.headers[consts.TOKEN_HEADER] = `bearer ${token}`
  139. return { url, options }
  140. }
  141. return { url, options }
  142. }
  143. const refreshTokenIfNeed = async (response, config) => {
  144. const res = await response.clone().json()
  145. if (
  146. res &&
  147. res.code !== consts.RET_CODE.SUCCESS &&
  148. !consts.TOKEN_INVALID_CODE.includes(res.code) &&
  149. config.url !== '/api/login'
  150. ) {
  151. message.error((res && res.msg) || '请求错误')
  152. // return Promise.reject(response)
  153. return response
  154. }
  155. if (res && res.code && consts.TOKEN_INVALID_CODE.includes(res.code)) {
  156. history.replace(consts.LOGIN_PATH)
  157. }
  158. return response
  159. }
  160. /**
  161. * 配置request请求时的默认参数
  162. */
  163. export const request: RequestConfig = {
  164. errorHandler,
  165. prefix: '/api',
  166. // 默认错误处理
  167. credentials: 'include', // 默认请求是否带上cookie
  168. prefix: consts.PREFIX_URL,
  169. cache: 'no-cache',
  170. responseInterceptors: [(response, options) => refreshTokenIfNeed(response, options)],
  171. requestInterceptors: [authHeaderInterceptor]
  172. }