user.js 2.8 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. import { STORAGE } from '@/core/constants/storage-keys'
  2. /**
  3. * 从登录响应里提炼真正的用户档案。
  4. * 多种历史形态在这里收敛,保证后续 spread 永远能拿到 token/id 等关键字段。
  5. */
  6. function pickUserProfile(payload) {
  7. if (!payload || typeof payload !== 'object') return {}
  8. if (payload.userinfo && typeof payload.userinfo === 'object') return payload.userinfo
  9. if (payload.data && typeof payload.data === 'object' && payload.data.userinfo) return payload.data.userinfo
  10. if (payload.token || payload.id) return payload
  11. return {}
  12. }
  13. const defaultState = () => ({
  14. id: 0,
  15. isLogin: false,
  16. username: '',
  17. nickname: '',
  18. mobile: '',
  19. avatar: '',
  20. level: 0,
  21. gender: 0,
  22. area_code: '852',
  23. birthday: '',
  24. bio: '',
  25. money: '0.00',
  26. score: 0,
  27. token: '',
  28. pushs: true,
  29. shock: true,
  30. voice: true
  31. })
  32. export default {
  33. namespaced: true,
  34. state: defaultState(),
  35. mutations: {
  36. apply(state, payload) {
  37. if (!payload || typeof payload !== 'object') return
  38. Object.keys(payload).forEach((key) => {
  39. if (key === 'token') {
  40. const next = payload.token
  41. const text = next != null ? String(next).trim() : ''
  42. // 仅在有有效 token 时写入;已登录时忽略空值,避免资料接口清空令牌
  43. if (text) state.token = text
  44. else if (!state.token) state.token = ''
  45. return
  46. }
  47. if (key === 'isLogin') {
  48. const on = payload.isLogin === true || payload.isLogin === 1 || payload.isLogin === '1'
  49. if (on) state.isLogin = true
  50. else if (!state.isLogin) state.isLogin = false
  51. return
  52. }
  53. state[key] = payload[key]
  54. })
  55. uni.setStorageSync(STORAGE.user, state)
  56. },
  57. reset(state) {
  58. Object.assign(state, defaultState())
  59. }
  60. },
  61. actions: {
  62. hydrateFromCache({ commit }) {
  63. const cached = uni.getStorageSync(STORAGE.user)
  64. if (cached) commit('apply', cached)
  65. },
  66. /**
  67. * 写入登录态。允许的 payload 形状:
  68. * - `{ userinfo: {...}, statistics: {...} }` 推荐形态
  69. * - `{ data: { userinfo: {...} } }` envelope 没拆干净时
  70. * - `{ id, token, nickname, ... }` 老接口扁平形态
  71. *
  72. * 写完 mutation 之后会再次 `setStorageSync`,确保 isLogin 被持久化
  73. * (和源项目 store/modules/user.js 行为一致,避免后续 token 拦截器读不到)。
  74. */
  75. login({ state, commit, dispatch }, payload = {}) {
  76. const profile = pickUserProfile(payload)
  77. commit('apply', {
  78. ...profile,
  79. isLogin: true,
  80. token: profile.token || state.token,
  81. pushs: true,
  82. voice: true,
  83. shock: true
  84. })
  85. if (!state.isLogin) state.isLogin = true
  86. if (profile.token && !state.token) state.token = profile.token
  87. uni.setStorageSync(STORAGE.user, state)
  88. const stats = payload && (payload.statistics || (payload.data && payload.data.statistics))
  89. if (stats) dispatch('stats/merge', stats, { root: true })
  90. }
  91. }
  92. }