refactor: 移除localStorage存储,改为基于cookie的状态保持
- 移除所有localStorage相关代码,不再保存敏感信息 - 前端UserInfo接口只保留后端实际返回的字段(user, user_type) - 更新getUserInfoApi和loginApi,只映射后端实际返回的字段 - 更新UserMenu组件,使用user字段替代username - 状态保持完全基于cookie验证
This commit is contained in:
parent
2afe515c5e
commit
2d7be8f7c4
@ -4,12 +4,7 @@ export interface LoginResponse {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export interface UserInfo {
|
export interface UserInfo {
|
||||||
id: string
|
user: string
|
||||||
username: string
|
|
||||||
email: string
|
|
||||||
avatar: string
|
|
||||||
first_name: string
|
|
||||||
last_name: string
|
|
||||||
user_type: string
|
user_type: string
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -63,26 +58,21 @@ export const loginApi = async (username: string, password: string): Promise<Logi
|
|||||||
const data = await response.json()
|
const data = await response.json()
|
||||||
|
|
||||||
if (response.status === 200 && (data.message === 'Logged In' || data.message === 'No App')) {
|
if (response.status === 200 && (data.message === 'Logged In' || data.message === 'No App')) {
|
||||||
const nameParts = (data.full_name || '').split(' ')
|
// 尝试获取用户信息
|
||||||
const userInfo: UserInfo = {
|
|
||||||
id: username,
|
|
||||||
username: username,
|
|
||||||
email: '',
|
|
||||||
avatar: '',
|
|
||||||
first_name: nameParts[0] || '',
|
|
||||||
last_name: nameParts.slice(1).join(' ') || '',
|
|
||||||
user_type: data.message === 'No App' ? 'Website User' : 'System User'
|
|
||||||
}
|
|
||||||
|
|
||||||
// 尝试获取更完整的用户信息
|
|
||||||
try {
|
try {
|
||||||
await new Promise(resolve => setTimeout(resolve, 200))
|
await new Promise(resolve => setTimeout(resolve, 200))
|
||||||
const detailedUserInfo = await getUserInfoApi()
|
const userInfo = await getUserInfoApi()
|
||||||
if (detailedUserInfo.id && detailedUserInfo.id !== 'Guest') {
|
if (userInfo.user && userInfo.user !== 'Guest') {
|
||||||
return { message: data.message, user: detailedUserInfo }
|
return { message: data.message, user: userInfo }
|
||||||
}
|
}
|
||||||
} catch {
|
} catch {
|
||||||
// API调用失败不影响登录
|
// API调用失败不影响登录,使用默认值
|
||||||
|
}
|
||||||
|
|
||||||
|
// 如果获取用户信息失败,使用默认值
|
||||||
|
const userInfo: UserInfo = {
|
||||||
|
user: username,
|
||||||
|
user_type: data.message === 'No App' ? 'Website User' : 'System User'
|
||||||
}
|
}
|
||||||
|
|
||||||
return { message: data.message, user: userInfo }
|
return { message: data.message, user: userInfo }
|
||||||
@ -117,16 +107,11 @@ export const getUserInfoApi = async (): Promise<UserInfo> => {
|
|||||||
const userInfo = data.message || data
|
const userInfo = data.message || data
|
||||||
|
|
||||||
const formattedUserInfo: UserInfo = {
|
const formattedUserInfo: UserInfo = {
|
||||||
id: userInfo.user || userInfo.name || userInfo.username || '',
|
user: userInfo.user || '',
|
||||||
username: userInfo.user || userInfo.name || userInfo.username || '',
|
|
||||||
email: userInfo.email || '',
|
|
||||||
avatar: userInfo.user_image || '',
|
|
||||||
first_name: userInfo.first_name || '',
|
|
||||||
last_name: userInfo.last_name || '',
|
|
||||||
user_type: userInfo.user_type || 'System User'
|
user_type: userInfo.user_type || 'System User'
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!formattedUserInfo.id || formattedUserInfo.id === 'Guest') {
|
if (!formattedUserInfo.user || formattedUserInfo.user === 'Guest') {
|
||||||
throw new Error('无法解析用户信息')
|
throw new Error('无法解析用户信息')
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -8,11 +8,10 @@
|
|||||||
<n-avatar
|
<n-avatar
|
||||||
round
|
round
|
||||||
size="small"
|
size="small"
|
||||||
:src="user?.avatar"
|
|
||||||
>
|
>
|
||||||
{{ user?.username?.charAt(0).toUpperCase() }}
|
{{ user?.user?.charAt(0).toUpperCase() }}
|
||||||
</n-avatar>
|
</n-avatar>
|
||||||
<span class="username">{{ user?.username }}</span>
|
<span class="username">{{ user?.user }}</span>
|
||||||
<Icon icon="tabler:chevron-down" />
|
<Icon icon="tabler:chevron-down" />
|
||||||
</n-button>
|
</n-button>
|
||||||
</n-dropdown>
|
</n-dropdown>
|
||||||
|
|||||||
@ -4,13 +4,8 @@ import { loginApi, getUserInfoApi, logoutApi, isCookieExpired, getSessionUser }
|
|||||||
import { setInitializingAuth } from '../utils/fetchInterceptor'
|
import { setInitializingAuth } from '../utils/fetchInterceptor'
|
||||||
|
|
||||||
export interface User {
|
export interface User {
|
||||||
id: string
|
user: string
|
||||||
username: string
|
user_type: string
|
||||||
email: string
|
|
||||||
avatar?: string
|
|
||||||
first_name?: string
|
|
||||||
last_name?: string
|
|
||||||
user_type?: string
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export const useAuthStore = defineStore('auth', () => {
|
export const useAuthStore = defineStore('auth', () => {
|
||||||
@ -28,39 +23,16 @@ export const useAuthStore = defineStore('auth', () => {
|
|||||||
error?.message?.includes('Cookie已过期')
|
error?.message?.includes('Cookie已过期')
|
||||||
}
|
}
|
||||||
|
|
||||||
// 设置用户状态(统一的状态更新方法)
|
// 设置用户状态(统一的状态更新方法,不保存到localStorage)
|
||||||
const setUserState = (userInfo: User) => {
|
const setUserState = (userInfo: User) => {
|
||||||
user.value = userInfo
|
user.value = userInfo
|
||||||
isAuthenticated.value = true
|
isAuthenticated.value = true
|
||||||
localStorage.setItem('jingrow_user', JSON.stringify(userInfo))
|
|
||||||
localStorage.setItem('jingrow_authenticated', 'true')
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 清除用户状态
|
// 清除用户状态
|
||||||
const clearUserState = () => {
|
const clearUserState = () => {
|
||||||
user.value = null
|
user.value = null
|
||||||
isAuthenticated.value = false
|
isAuthenticated.value = false
|
||||||
localStorage.removeItem('jingrow_user')
|
|
||||||
localStorage.removeItem('jingrow_authenticated')
|
|
||||||
}
|
|
||||||
|
|
||||||
// 从localStorage恢复用户状态
|
|
||||||
const restoreUserFromStorage = (): User | null => {
|
|
||||||
const savedUser = localStorage.getItem('jingrow_user')
|
|
||||||
const savedAuth = localStorage.getItem('jingrow_authenticated')
|
|
||||||
|
|
||||||
if (savedUser && savedAuth === 'true') {
|
|
||||||
try {
|
|
||||||
const parsedUser = JSON.parse(savedUser)
|
|
||||||
user.value = parsedUser
|
|
||||||
isAuthenticated.value = true
|
|
||||||
return parsedUser
|
|
||||||
} catch (error) {
|
|
||||||
console.error('解析保存的用户信息失败:', error)
|
|
||||||
clearUserState()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return null
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 验证并更新用户信息
|
// 验证并更新用户信息
|
||||||
@ -116,20 +88,16 @@ export const useAuthStore = defineStore('auth', () => {
|
|||||||
const hasSessionCookie = !isCookieExpired()
|
const hasSessionCookie = !isCookieExpired()
|
||||||
const hasCookie = userId || hasSessionCookie
|
const hasCookie = userId || hasSessionCookie
|
||||||
|
|
||||||
// 尝试从localStorage恢复状态(避免闪烁)
|
// 如果没有cookie,清除认证状态
|
||||||
const savedUser = restoreUserFromStorage()
|
if (!hasCookie) {
|
||||||
const hasSavedState = !!savedUser
|
|
||||||
|
|
||||||
// 如果既没有cookie也没有保存的状态,清除认证
|
|
||||||
if (!hasCookie && !hasSavedState) {
|
|
||||||
if (isAuthenticated.value) {
|
if (isAuthenticated.value) {
|
||||||
clearUserState()
|
clearUserState()
|
||||||
}
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// 如果有cookie或保存的状态,尝试验证
|
// 如果有cookie,尝试验证并获取用户信息
|
||||||
if (hasCookie || hasSavedState) {
|
if (hasCookie) {
|
||||||
await validateAndUpdateUser()
|
await validateAndUpdateUser()
|
||||||
}
|
}
|
||||||
} finally {
|
} finally {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user