user.ts
4.62 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
import { defineStore } from 'pinia'
import { ref, computed } from 'vue'
import { ElMessage } from 'element-plus'
import type { User, LoginForm, LoginResponse } from '@/types'
import { loginApi, getUserInfoApi, logoutApi } from '@/api/auth'
import { getToken, setToken, removeToken, setUserInfo, getUserInfo, clearAuth } from '@/utils/auth'
export const useUserStore = defineStore('user', () => {
// 状态
const token = ref<string>(getToken() || '')
const userInfo = ref<User | null>(getUserInfo())
const permissions = ref<string[]>([])
const roles = ref<string[]>([])
// 计算属性
const isLoggedIn = computed(() => !!token.value)
const username = computed(() => userInfo.value?.username || '')
const avatar = computed(() => userInfo.value?.avatar || '')
// 登录
const login = async (loginForm: LoginForm): Promise<void> => {
try {
const response: LoginResponse = await loginApi(loginForm)
// 保存token和用户信息
token.value = response.token
userInfo.value = response.userInfo
permissions.value = response.userInfo.permissions || []
roles.value = response.userInfo.roles?.map(role => role.roleKey) || []
// 持久化存储
setToken(response.token)
setUserInfo(response.userInfo)
ElMessage.success('登录成功')
// 跳转到首页
window.location.href = '/'
} catch (error) {
console.error('登录失败:', error)
throw error
}
}
// 获取用户信息
const getUserInfoAction = async (): Promise<void> => {
try {
if (!token.value) return
const response: User = await getUserInfoApi()
userInfo.value = response
permissions.value = response.permissions || []
roles.value = response.roles?.map(role => role.roleKey) || []
// 更新本地存储
setUserInfo(response)
// 获取用户信息后,加载用户菜单权限
if (response.userId) {
// 动态导入避免循环依赖
const { usePermissionStore } = await import('./permission')
const permissionStore = usePermissionStore()
await permissionStore.getUserPermissionMenus(response.userId)
}
} catch (error) {
console.error('获取用户信息失败:', error)
// 如果获取用户信息失败,可能是token过期,清除认证信息
logout()
}
}
// 登出
const logout = async (): Promise<void> => {
try {
if (token.value) {
await logoutApi()
}
} catch (error) {
console.error('登出请求失败:', error)
} finally {
// 清除状态
token.value = ''
userInfo.value = null
permissions.value = []
roles.value = []
// 清除权限store中的菜单
try {
const { usePermissionStore } = await import('./permission')
const permissionStore = usePermissionStore()
permissionStore.resetState()
} catch (error) {
console.error('清除权限store失败:', error)
}
// 清除本地存储
clearAuth()
// 跳转到登录页
window.location.href = '/login'
}
}
// 检查权限
const hasPermission = (permission: string): boolean => {
if (!permission) return true
return permissions.value.includes(permission)
}
// 检查角色
const hasRole = (role: string): boolean => {
if (!role) return true
return roles.value.includes(role)
}
// 检查是否有任意一个权限
const hasAnyPermission = (permissionList: string[]): boolean => {
if (!permissionList || permissionList.length === 0) return true
return permissionList.some(permission => permissions.value.includes(permission))
}
// 检查是否有所有权限
const hasAllPermissions = (permissionList: string[]): boolean => {
if (!permissionList || permissionList.length === 0) return true
return permissionList.every(permission => permissions.value.includes(permission))
}
// 更新用户信息
const updateUserInfo = (newUserInfo: Partial<User>): void => {
if (userInfo.value) {
userInfo.value = { ...userInfo.value, ...newUserInfo }
setUserInfo(userInfo.value)
}
}
// 重置状态
const resetState = (): void => {
token.value = ''
userInfo.value = null
permissions.value = []
roles.value = []
}
return {
// 状态
token,
userInfo,
permissions,
roles,
// 计算属性
isLoggedIn,
username,
avatar,
// 方法
login,
getUserInfoAction,
logout,
hasPermission,
hasRole,
hasAnyPermission,
hasAllPermissions,
updateUserInfo,
resetState
}
})