创建 src/api/interface/account.interface.ts
创建 src/api 文件夹的目的:项目内所有的API请求,都会放在 src/api 中;
创建 src/api/interface 文件夹的目的:项目内所有的API请求的参数和返回值的接口约束,都会放在 src/api/interface 中;
创建 src/api/interface/account.interface.ts 文件夹的目的:当前登录账号相关的API请求的参数和返回值的接口约束,都会放在 src/api/interface/account.interface.ts 中;
// src/api/interface/account.interface.ts
/**
* 登录参数
*/
export interface LoginParamsModel {
username: string
password: string
};
/**
* 登录返回结果
*/
export interface LoginResModel {
token: string
};
/**
* 当前登录账号的详细信息
*/
export interface UserInfoModel {
username: string
nickname: string
avatar: string
email: string
phone: string
remark: string
id: number
createdAt: string
updatedAt: string
};
创建 src/api/enum/common.enum.ts
创建目的: 项目内所有的API请求能用到的枚举约束
// src/api/enum/common.enum.ts
/**
* API 请求返回 code 码枚举类型
*/
export enum ResCodeEnum {
// 操作成功
SUCCESS = 0,
// 操作失败
FAIL = -1,
// 未登录
NOT_LOGIN = -2,
// token 过期
TOKEN_EXPIRATION = -3,
}
创建 src/api/interface/common.interface.ts
创建目的: 项目内所有的API请求能用到的公共接口约束
// src/api/interface/common.interface.ts
import type { ResCodeEnum } from '../enum/common.enum'
/**
* 响应数据模型
*/
export interface ResCodeMsg<D> {
data: D
code: ResCodeEnum
message: string
}
创建 src/api/account.ts
创建目的:当前登录账号相关的API请求,都会放在 src/api/account.ts 中
// src/api/account.ts
import type { LoginParamsModel, LoginResModel, UserInfoModel } from './interface/account.interface'
import type { ResCodeMsg } from './interface/common.interface'
import { ResCodeEnum } from './enum/common.enum'
/**
* 登录
*/
export function accountLogin(data: LoginParamsModel): Promise<ResCodeMsg<LoginResModel>> {
console.log('loginParams', data)
// 目前还没有定义 axios 请求, 先暂时模拟一下请求
return new Promise((resolve) => {
const timer = setTimeout(() => {
clearTimeout(timer)
resolve({
code: ResCodeEnum.SUCCESS,
message: '登录成功',
data: {
token: 'mock_token',
},
})
}, 1000)
})
}
/** 获取账户资料 */
export async function accountProfile(): Promise<ResCodeMsg<UserInfoModel>> {
// 目前还没有定义 axios 请求, 先暂时模拟一下请求
return new Promise((resolve) => {
const timer = setTimeout(() => {
clearTimeout(timer)
resolve({
code: ResCodeEnum.SUCCESS,
message: '登录成功',
data: {
username: '萧炎',
nickname: '侥幸哥',
avatar: '',
email: '123456@qq.com',
phone: '12345678901',
remark: '备注信息',
id: 1,
createdAt: '2025-08-04 09:52:43',
updatedAt: '',
},
})
}, 1000)
})
}
/** 退出登录 */
export function accountLogout(): Promise<ResCodeMsg<null>> {
// 目前还没有定义 axios 请求, 先暂时模拟一下请求
return new Promise((resolve) => {
const timer = setTimeout(() => {
clearTimeout(timer)
resolve({
code: ResCodeEnum.SUCCESS,
message: '退出登录成功',
data: null,
})
}, 1000)
})
}
创建 src/store/modules/user.ts 并实现 useUserStore
import type { LoginParamsModel, UserInfoModel } from '@/api/interface/account.interface'
import { defineStore } from 'pinia'
import { ref } from 'vue'
import { accountLogin, accountLogout, accountProfile } from '@/api/account'
import { ResCodeEnum } from '@/api/enum/common.enum'
export const useUserStore = defineStore(
'user',
() => {
const token = ref<string>()
const userInfo = ref<Partial<UserInfoModel>>({})
/** 清空登录态 */
const clearLoginStatus = () => {
token.value = '';
userInfo.value = {};
localStorage.clear();
};
/** 登录成功保存token */
const setToken = (_token: string) => {
token.value = _token
}
/** 登录成功之后, 获取用户信息 */
const afterLogin = async () => {
try {
const response= await accountProfile()
if (response.code !== ResCodeEnum.SUCCESS) {
message.warning(response.message)
return;
}
userInfo.value = response.data
}
catch (error) {
return Promise.reject(error)
}
}
/** 登录 */
const login = async (params: LoginParamsModel) => {
try {
const response= await accountLogin(params)
if (response.code !== ResCodeEnum.SUCCESS) {
message.warning(response.message)
return
}
setToken(response.data.token)
await afterLogin()
}
catch (error) {
return Promise.reject(error)
}
}
/** 登出 */
const logout = async () => {
await accountLogout()
clearLoginStatus()
}
return { token, userInfo, login, afterLogin, logout, clearLoginStatus };
},
{
persist: {
// 只将 token 和 userInfo 持久化到本地缓存中
pick: ['token', 'userInfo'],
},
}
);