refactor: ♻️ 重构API为静态方法实现模块化管理,并将types.ts重命名为model.ts用于存放接口模型定义

This commit is contained in:
hxr
2024-05-04 12:53:08 +08:00
parent a211053176
commit 088bc5e48f
37 changed files with 875 additions and 831 deletions

View File

@@ -1,44 +1,48 @@
import request from "@/utils/request";
import { CaptchaResult, LoginData, LoginResult } from "./types";
import { CaptchaResult, LoginData, LoginResult } from "./model";
/**
* 登录API
*
* @param data {LoginData}
* @returns
*/
export function loginApi(data: LoginData) {
const formData = new FormData();
formData.append("username", data.username);
formData.append("password", data.password);
formData.append("captchaKey", data.captchaKey || "");
formData.append("captchaCode", data.captchaCode || "");
return request<any, ResponseData<LoginResult>>({
url: "/api/v1/auth/login",
method: "post",
data: formData,
headers: {
"Content-Type": "multipart/form-data",
},
});
class AuthAPI {
/**
* 登录API
*
* @param data {LoginData}
* @returns
*/
static login(data: LoginData) {
const formData = new FormData();
formData.append("username", data.username);
formData.append("password", data.password);
formData.append("captchaKey", data.captchaKey || "");
formData.append("captchaCode", data.captchaCode || "");
return request<any, LoginResult>({
url: "/api/v1/auth/login",
method: "post",
data: formData,
headers: {
"Content-Type": "multipart/form-data",
},
});
}
/**
* 注销API
*/
static logout() {
return request({
url: "/api/v1/auth/logout",
method: "delete",
});
}
/**
* 获取验证码
*/
static getCaptcha() {
return request<any, CaptchaResult>({
url: "/api/v1/auth/captcha",
method: "get",
});
}
}
/**
* 注销API
*/
export function logoutApi() {
return request({
url: "/api/v1/auth/logout",
method: "delete",
});
}
/**
* 获取验证码
*/
export function getCaptchaApi() {
return request<any, ResponseData<CaptchaResult>>({
url: "/api/v1/auth/captcha",
method: "get",
});
}
export default AuthAPI;

View File

@@ -1,76 +1,80 @@
import request from "@/utils/request";
import { DeptForm, DeptQuery, DeptVO } from "./types";
import { DeptForm, DeptQuery, DeptVO } from "./model";
/**
* 部门树形表格
*
* @param queryParams
*/
export function listDepts(queryParams?: DeptQuery) {
return request<any, ResponseData<DeptVO[]>>({
url: "/api/v1/dept",
method: "get",
params: queryParams,
});
class DeptAPI {
/**
* 部门树形表格
*
* @param queryParams
*/
static getList(queryParams?: DeptQuery) {
return request<any, DeptVO[]>({
url: "/api/v1/dept",
method: "get",
params: queryParams,
});
}
/**
* 部门下拉列表
*/
static getOptions() {
return request<any, OptionType[]>({
url: "/api/v1/dept/options",
method: "get",
});
}
/**
* 获取部门详情
*
* @param id
*/
static getFormData(id: number) {
return request<any, DeptForm>({
url: "/api/v1/dept/" + id + "/form",
method: "get",
});
}
/**
* 新增部门
*
* @param data
*/
static add(data: DeptForm) {
return request({
url: "/api/v1/dept",
method: "post",
data: data,
});
}
/**
* 修改部门
*
* @param id
* @param data
*/
static update(id: number, data: DeptForm) {
return request({
url: "/api/v1/dept/" + id,
method: "put",
data: data,
});
}
/**
* 删除部门
*
* @param ids
*/
static deleteByIds(ids: string) {
return request({
url: "/api/v1/dept/" + ids,
method: "delete",
});
}
}
/**
* 部门下拉列表
*/
export function getDeptOptions() {
return request<any, ResponseData<OptionType[]>>({
url: "/api/v1/dept/options",
method: "get",
});
}
/**
* 获取部门详情
*
* @param id
*/
export function getDeptForm(id: number) {
return request<any, ResponseData<DeptForm>>({
url: "/api/v1/dept/" + id + "/form",
method: "get",
});
}
/**
* 新增部门
*
* @param data
*/
export function addDept(data: DeptForm) {
return request({
url: "/api/v1/dept",
method: "post",
data: data,
});
}
/**
* 修改部门
*
* @param id
* @param data
*/
export function updateDept(id: number, data: DeptForm) {
return request({
url: "/api/v1/dept/" + id,
method: "put",
data: data,
});
}
/**
* 删除部门
*
* @param ids
*/
export function deleteDept(ids: string) {
return request({
url: "/api/v1/dept/" + ids,
method: "delete",
});
}
export default DeptAPI;

View File

@@ -6,140 +6,144 @@ import {
DictQuery,
DictForm,
DictPageResult,
} from "./types";
} from "./model";
/**
* 字典类型分页列表
*
* @param queryParams
*/
export function getDictTypePage(queryParams: DictTypeQuery) {
return request<any, ResponseData<DictTypePageResult>>({
url: "/api/v1/dict/types/page",
method: "get",
params: queryParams,
});
class DictAPI {
/**
* 字典类型分页列表
*
* @param queryParams
*/
static getDictTypePage(queryParams: DictTypeQuery) {
return request<any, DictTypePageResult>({
url: "/api/v1/dict/types/page",
method: "get",
params: queryParams,
});
}
/**
* 字典类型表单数据
*
* @param id
*/
static getDictTypeForm(id: number) {
return request<any, ResponseData<DictTypeForm>>({
url: "/api/v1/dict/types/" + id + "/form",
method: "get",
});
}
/**
* 新增字典类型
*
* @param data
*/
static addDictType(data: DictTypeForm) {
return request({
url: "/api/v1/dict/types",
method: "post",
data: data,
});
}
/**
* 修改字典类型
*
* @param id
* @param data
*/
static updateDictType(id: number, data: DictTypeForm) {
return request({
url: "/api/v1/dict/types/" + id,
method: "put",
data: data,
});
}
/**
* 删除字典类型
*/
static deleteDictTypes(ids: string) {
return request({
url: "/api/v1/dict/types/" + ids,
method: "delete",
});
}
/**
* 获取字典类型的数据项
*
* @param typeCode 字典类型编码
*/
static getDictOptions(typeCode: string) {
return request<any, OptionType[]>({
url: "/api/v1/dict/" + typeCode + "/options",
method: "get",
});
}
/**
* 字典分页列表
*/
static getDictPage(queryParams: DictQuery) {
return request<any, DictPageResult>({
url: "/api/v1/dict/page",
method: "get",
params: queryParams,
});
}
/**
* 获取字典表单数据
*
* @param id
*/
static getDictFormData(id: number) {
return request<any, DictForm>({
url: "/api/v1/dict/" + id + "/form",
method: "get",
});
}
/**
* 新增字典
*
* @param data
*/
static addDict(data: DictForm) {
return request({
url: "/api/v1/dict",
method: "post",
data: data,
});
}
/**
* 修改字典项
*
* @param id
* @param data
*/
static updateDict(id: number, data: DictForm) {
return request({
url: "/api/v1/dict/" + id,
method: "put",
data: data,
});
}
/**
* 删除字典
*
* @param ids 字典项ID多个以英文逗号(,)分割
*/
static deleteDictByIds(ids: string) {
return request({
url: "/api/v1/dict/" + ids,
method: "delete",
});
}
}
/**
* 字典类型表单数据
*
* @param id
*/
export function getDictTypeForm(id: number) {
return request<any, ResponseData<DictTypeForm>>({
url: "/api/v1/dict/types/" + id + "/form",
method: "get",
});
}
/**
* 新增字典类型
*
* @param data
*/
export function addDictType(data: DictTypeForm) {
return request({
url: "/api/v1/dict/types",
method: "post",
data: data,
});
}
/**
* 修改字典类型
*
* @param id
* @param data
*/
export function updateDictType(id: number, data: DictTypeForm) {
return request({
url: "/api/v1/dict/types/" + id,
method: "put",
data: data,
});
}
/**
* 删除字典类型
*/
export function deleteDictTypes(ids: string) {
return request({
url: "/api/v1/dict/types/" + ids,
method: "delete",
});
}
/**
* 获取字典类型的数据项
*
* @param typeCode 字典类型编码
*/
export function getDictOptions(typeCode: string) {
return request<any, ResponseData<OptionType[]>>({
url: "/api/v1/dict/" + typeCode + "/options",
method: "get",
});
}
/**
* 字典分页列表
*/
export function getDictPage(queryParams: DictQuery) {
return request<any, ResponseData<DictPageResult>>({
url: "/api/v1/dict/page",
method: "get",
params: queryParams,
});
}
/**
* 获取字典表单数据
*
* @param id
*/
export function getDictFormData(id: number) {
return request<any, ResponseData<DictForm>>({
url: "/api/v1/dict/" + id + "/form",
method: "get",
});
}
/**
* 新增字典
*
* @param data
*/
export function addDict(data: DictForm) {
return request({
url: "/api/v1/dict",
method: "post",
data: data,
});
}
/**
* 修改字典项
*
* @param id
* @param data
*/
export function updateDict(id: number, data: DictForm) {
return request({
url: "/api/v1/dict/" + id,
method: "put",
data: data,
});
}
/**
* 删除字典
*
* @param ids 字典项ID多个以英文逗号(,)分割
*/
export function deleteDict(ids: string) {
return request({
url: "/api/v1/dict/" + ids,
method: "delete",
});
}
export default DictAPI;

View File

@@ -1,33 +1,37 @@
import request from "@/utils/request";
import { FileInfo } from "./types";
import { FileInfo } from "./model";
/**
* 上传文件
*
* @param file
*/
export function uploadFileApi(file: File) {
const formData = new FormData();
formData.append("file", file);
return request<any, ResponseData<FileInfo>>({
url: "/api/v1/files",
method: "post",
data: formData,
headers: {
"Content-Type": "multipart/form-data",
},
});
class FileAPI {
/**
* 上传文件
*
* @param file
*/
static upload(file: File) {
const formData = new FormData();
formData.append("file", file);
return request<any, FileInfo>({
url: "/api/v1/files",
method: "post",
data: formData,
headers: {
"Content-Type": "multipart/form-data",
},
});
}
/**
* 删除文件
*
* @param filePath 文件完整路径
*/
static deleteByPath(filePath?: string) {
return request({
url: "/api/v1/files",
method: "delete",
params: { filePath: filePath },
});
}
}
/**
* 删除文件
*
* @param filePath 文件完整路径
*/
export function deleteFileApi(filePath?: string) {
return request({
url: "/api/v1/files",
method: "delete",
params: { filePath: filePath },
});
}
export default FileAPI;

View File

@@ -1,87 +1,90 @@
import request from "@/utils/request";
import type { RouteRecordRaw } from "vue-router";
import { MenuQuery, MenuVO, MenuForm } from "./types";
import { MenuQuery, MenuVO, MenuForm, RouteVO } from "./model";
/**
* 获取路由列表
*/
export function listRoutes() {
return request<any, ResponseData<RouteRecordRaw[]>>({
url: "/api/v1/menus/routes",
method: "get",
});
class MenuAPI {
/**
* 获取路由列表
*/
static getRoutes() {
return request<any, RouteVO[]>({
url: "/api/v1/menus/routes",
method: "get",
});
}
/**
* 获取菜单树形列表
*
* @param queryParams
*/
static getList(queryParams: MenuQuery) {
return request<any, MenuVO[]>({
url: "/api/v1/menus",
method: "get",
params: queryParams,
});
}
/**
* 获取菜单下拉数据源
*/
static getOptions() {
return request<any, OptionType[]>({
url: "/api/v1/menus/options",
method: "get",
});
}
/**
* 获取菜单表单数据
*
* @param id
*/
static getFormData(id: number) {
return request<any, MenuForm>({
url: "/api/v1/menus/" + id + "/form",
method: "get",
});
}
/**
* 添加菜单
*
* @param data
*/
static add(data: MenuForm) {
return request({
url: "/api/v1/menus",
method: "post",
data: data,
});
}
/**
* 修改菜单
*
* @param id
* @param data
*/
static update(id: string, data: MenuForm) {
return request({
url: "/api/v1/menus/" + id,
method: "put",
data: data,
});
}
/**
* 删除菜单
*
* @param id 菜单ID
*/
static deleteById(id: number) {
return request({
url: "/api/v1/menus/" + id,
method: "delete",
});
}
}
/**
* 获取菜单树形列表
*
* @param queryParams
*/
export function listMenus(queryParams: MenuQuery) {
return request<any, ResponseData<MenuVO[]>>({
url: "/api/v1/menus",
method: "get",
params: queryParams,
});
}
/**
* 获取菜单下拉树形列表
*/
export function getMenuOptions() {
return request<any, ResponseData<OptionType[]>>({
url: "/api/v1/menus/options",
method: "get",
});
}
/**
* 获取菜单表单数据
*
* @param id
*/
export function getMenuForm(id: number) {
return request<any, ResponseData<MenuForm>>({
url: "/api/v1/menus/" + id + "/form",
method: "get",
});
}
/**
* 添加菜单
*
* @param data
*/
export function addMenu(data: MenuForm) {
return request({
url: "/api/v1/menus",
method: "post",
data: data,
});
}
/**
* 修改菜单
*
* @param id
* @param data
*/
export function updateMenu(id: string, data: MenuForm) {
return request({
url: "/api/v1/menus/" + id,
method: "put",
data: data,
});
}
/**
* 删除菜单
*
* @param id 菜单ID
*/
export function deleteMenu(id: number) {
return request({
url: "/api/v1/menus/" + id,
method: "delete",
});
}
export default MenuAPI;

View File

@@ -122,3 +122,60 @@ export interface MenuForm {
*/
alwaysShow?: number;
}
/**
* RouteVO
*/
export interface RouteVO {
/**
*
*/
children: RouteVO[];
/**
*
*/
component?: string;
meta?: Meta;
/**
*
*/
name?: string;
/**
*
*/
path?: string;
/**
*
*/
redirect?: string;
}
/**
* Meta
*/
export interface Meta {
/**
*
*/
alwaysShow?: boolean;
/**
* (true- false-)
*/
hidden?: boolean;
/**
* ICON
*/
icon?: string;
/**
*
*/
keepAlive?: boolean;
/**
*
*/
roles?: string[];
/**
* title
*/
title?: string;
}

View File

@@ -1,104 +1,108 @@
import request from "@/utils/request";
import { RoleQuery, RolePageResult, RoleForm } from "./types";
import { RoleQuery, RolePageResult, RoleForm } from "./model";
/**
* 获取角色分页数据
*
* @param queryParams
*/
export function getRolePage(queryParams?: RoleQuery) {
return request<any, ResponseData<RolePageResult>>({
url: "/api/v1/roles/page",
method: "get",
params: queryParams,
});
class RoleAPI {
/**
* 获取角色分页数据
*
* @param queryParams
*/
static getPage(queryParams?: RoleQuery) {
return request<any, RolePageResult>({
url: "/api/v1/roles/page",
method: "get",
params: queryParams,
});
}
/**
* 获取角色下拉数据源
*
* @param queryParams
*/
static getOptions(queryParams?: RoleQuery) {
return request<any, OptionType[]>({
url: "/api/v1/roles/options",
method: "get",
params: queryParams,
});
}
/**
* 获取角色的菜单ID集合
*
* @param queryParams
*/
static getRoleMenuIds(roleId: number) {
return request<any, number[]>({
url: "/api/v1/roles/" + roleId + "/menuIds",
method: "get",
});
}
/**
* 分配菜单权限给角色
*
* @param queryParams
*/
static updateRoleMenus(roleId: number, data: number[]) {
return request({
url: "/api/v1/roles/" + roleId + "/menus",
method: "put",
data: data,
});
}
/**
* 获取角色表单数据
*
* @param id
*/
static getFormData(id: number) {
return request<any, RoleForm>({
url: "/api/v1/roles/" + id + "/form",
method: "get",
});
}
/**
* 添加角色
*
* @param data
*/
static add(data: RoleForm) {
return request({
url: "/api/v1/roles",
method: "post",
data: data,
});
}
/**
* 更新角色
*
* @param id
* @param data
*/
static update(id: number, data: RoleForm) {
return request({
url: "/api/v1/roles/" + id,
method: "put",
data: data,
});
}
/**
* 批量删除角色,多个以英文逗号(,)分割
*
* @param ids
*/
static deleteByIds(ids: string) {
return request({
url: "/api/v1/roles/" + ids,
method: "delete",
});
}
}
/**
* 获取角色下拉数据
*
* @param queryParams
*/
export function getRoleOptions(queryParams?: RoleQuery) {
return request<any, ResponseData<OptionType[]>>({
url: "/api/v1/roles/options",
method: "get",
params: queryParams,
});
}
/**
* 获取角色的菜单ID集合
*
* @param queryParams
*/
export function getRoleMenuIds(roleId: number) {
return request<any, ResponseData<number[]>>({
url: "/api/v1/roles/" + roleId + "/menuIds",
method: "get",
});
}
/**
* 分配菜单权限给角色
*
* @param queryParams
*/
export function updateRoleMenus(roleId: number, data: number[]) {
return request({
url: "/api/v1/roles/" + roleId + "/menus",
method: "put",
data: data,
});
}
/**
* 获取角色详情
*
* @param id
*/
export function getRoleForm(id: number) {
return request<any, ResponseData<RoleForm>>({
url: "/api/v1/roles/" + id + "/form",
method: "get",
});
}
/**
* 添加角色
*
* @param data
*/
export function addRole(data: RoleForm) {
return request({
url: "/api/v1/roles",
method: "post",
data: data,
});
}
/**
* 更新角色
*
* @param id
* @param data
*/
export function updateRole(id: number, data: RoleForm) {
return request({
url: "/api/v1/roles/" + id,
method: "put",
data: data,
});
}
/**
* 批量删除角色,多个以英文逗号(,)分割
*
* @param ids
*/
export function deleteRoles(ids: string) {
return request({
url: "/api/v1/roles/" + ids,
method: "delete",
});
}
export default RoleAPI;

View File

@@ -1,137 +1,141 @@
import request from "@/utils/request";
import { UserForm, UserInfo, UserPageVO, UserQuery } from "./types";
import { UserForm, UserInfo, UserPageVO, UserQuery } from "./model";
/**
* 登录成功后获取用户信息(昵称、头像、权限集合和角色集合)
*/
export function getUserInfoApi() {
return request<any, ResponseData<UserInfo>>({
url: "/api/v1/users/me",
method: "get",
});
class UserAPI {
/**
* 登录成功后获取用户信息(昵称、头像、权限集合和角色集合)
*/
static getInfo() {
return request<any, UserInfo>({
url: "/api/v1/users/me",
method: "get",
});
}
/**
* 获取用户分页列表
*
* @param queryParams
*/
static getPage(queryParams: UserQuery) {
return request<any, PageResult<UserPageVO[]>>({
url: "/api/v1/users/page",
method: "get",
params: queryParams,
});
}
/**
* 获取用户表单详情
*
* @param userId
*/
static getFormData(userId: number) {
return request<any, UserForm>({
url: "/api/v1/users/" + userId + "/form",
method: "get",
});
}
/**
* 添加用户
*
* @param data
*/
static add(data: UserForm) {
return request({
url: "/api/v1/users",
method: "post",
data: data,
});
}
/**
* 修改用户
*
* @param id
* @param data
*/
static update(id: number, data: UserForm) {
return request({
url: "/api/v1/users/" + id,
method: "put",
data: data,
});
}
/**
* 修改用户密码
*
* @param id
* @param password
*/
static updatePassword(id: number, password: string) {
return request({
url: "/api/v1/users/" + id + "/password",
method: "patch",
params: { password: password },
});
}
/**
* 删除用户
*
* @param ids
*/
static deleteByIds(ids: string) {
return request({
url: "/api/v1/users/" + ids,
method: "delete",
});
}
/**
* 下载用户导入模板
*
* @returns
*/
static downloadTemplate() {
return request({
url: "/api/v1/users/template",
method: "get",
responseType: "arraybuffer",
});
}
/**
* 导出用户
*
* @param queryParams
* @returns
*/
static export(queryParams: UserQuery) {
return request({
url: "/api/v1/users/export",
method: "get",
params: queryParams,
responseType: "arraybuffer",
});
}
/**
* 导入用户
*
* @param file
*/
static import(deptId: number, file: File) {
const formData = new FormData();
formData.append("file", file);
return request({
url: "/api/v1/users/import",
method: "post",
params: { deptId: deptId },
data: formData,
headers: {
"Content-Type": "multipart/form-data",
},
});
}
}
/**
* 获取用户分页列表
*
* @param queryParams
*/
export function getUserPage(queryParams: UserQuery) {
return request<any, ResponseData<PageResult<UserPageVO[]>>>({
url: "/api/v1/users/page",
method: "get",
params: queryParams,
});
}
/**
* 获取用户表单详情
*
* @param userId
*/
export function getUserForm(userId: number) {
return request<any, ResponseData<UserForm>>({
url: "/api/v1/users/" + userId + "/form",
method: "get",
});
}
/**
* 添加用户
*
* @param data
*/
export function addUser(data: UserForm) {
return request({
url: "/api/v1/users",
method: "post",
data: data,
});
}
/**
* 修改用户
*
* @param id
* @param data
*/
export function updateUser(id: number, data: UserForm) {
return request({
url: "/api/v1/users/" + id,
method: "put",
data: data,
});
}
/**
* 修改用户密码
*
* @param id
* @param password
*/
export function updateUserPassword(id: number, password: string) {
return request({
url: "/api/v1/users/" + id + "/password",
method: "patch",
params: { password: password },
});
}
/**
* 删除用户
*
* @param ids
*/
export function deleteUsers(ids: string) {
return request({
url: "/api/v1/users/" + ids,
method: "delete",
});
}
/**
* 下载用户导入模板
*
* @returns
*/
export function downloadTemplateApi() {
return request({
url: "/api/v1/users/template",
method: "get",
responseType: "arraybuffer",
});
}
/**
* 导出用户
*
* @param queryParams
* @returns
*/
export function exportUser(queryParams: UserQuery) {
return request({
url: "/api/v1/users/_export",
method: "get",
params: queryParams,
responseType: "arraybuffer",
});
}
/**
* 导入用户
*
* @param file
*/
export function importUser(deptId: number, file: File) {
const formData = new FormData();
formData.append("file", file);
return request({
url: "/api/v1/users/_import",
method: "post",
params: { deptId: deptId },
data: formData,
headers: {
"Content-Type": "multipart/form-data",
},
});
}
export default UserAPI;

View File

@@ -16,7 +16,7 @@
</template>
<script setup lang="ts">
import { getDictOptions } from "@/api/dict";
import DictAPI from "@/api/dict";
const props = defineProps({
/**
@@ -66,8 +66,8 @@ function handleChange(val?: string | number | undefined) {
onBeforeMount(() => {
// 根据字典类型编码(typeCode)获取字典选项
getDictOptions(props.typeCode).then((response) => {
options.value = response.data;
DictAPI.getDictOptions(props.typeCode).then((data) => {
options.value = data;
});
});
</script>

View File

@@ -265,7 +265,7 @@ function fetchPageData(formData: IObject = {}, isRestart = false) {
}
props.contentConfig
.indexAction({ ...queryParams, ...formData })
.then(({ data }) => {
.then((data) => {
total.value = data.total;
pageData.value = data.list;
})

View File

@@ -1,9 +1,4 @@
<!--
多图上传组件
@author: youlaitech
@date 2022/11/20
-->
<!-- 多图上传组件 -->
<template>
<el-upload
v-model:file-list="fileList"
@@ -30,7 +25,7 @@ import {
UploadFile,
UploadProps,
} from "element-plus";
import { uploadFileApi, deleteFileApi } from "@/api/file";
import FileAPI from "@/api/file";
const emit = defineEmits(["update:modelValue"]);
@@ -83,7 +78,7 @@ watch(
*/
async function handleUpload(options: UploadRequestOptions): Promise<any> {
// 上传API调用
const { data: fileInfo } = await uploadFileApi(options.file);
const { data: fileInfo } = await FileAPI.upload(options.file);
// 上传成功需手动替换文件路径为远程URL否则图片地址为预览地址 blob:http://
const fileIndex = fileList.value.findIndex(
@@ -108,7 +103,7 @@ function handleRemove(removeFile: UploadFile) {
const filePath = removeFile.url;
if (filePath) {
deleteFileApi(filePath).then(() => {
FileAPI.deleteByPath(filePath).then(() => {
// 删除成功回调
emit(
"update:modelValue",

View File

@@ -15,7 +15,7 @@
<script setup lang="ts">
import { UploadRawFile, UploadRequestOptions } from "element-plus";
import { uploadFileApi } from "@/api/file";
import FileAPI from "@/api/file";
const props = defineProps({
modelValue: {
@@ -33,7 +33,7 @@ const imgUrl = useVModel(props, "modelValue", emit);
* @param options
*/
async function uploadFile(options: UploadRequestOptions): Promise<any> {
const { data: fileInfo } = await uploadFileApi(options.file);
const { data: fileInfo } = await FileAPI.update(options.file);
imgUrl.value = fileInfo.url;
}

4
src/enums/CacheEnum.ts Normal file
View File

@@ -0,0 +1,4 @@
/**
* 令牌缓存Key
*/
export const TOKEN_KEY = "accessToken";

18
src/enums/ResultEnum.ts Normal file
View File

@@ -0,0 +1,18 @@
/**
* 响应码枚举
*/
export const enum ResultEnum {
/**
* 成功
*/
SUCCESS = "00000",
/**
* 错误
*/
ERROR = "B0001",
/**
* 令牌无效或过期
*/
TOKEN_INVALID = "A0230",
}

View File

@@ -2,6 +2,7 @@ import router from "@/router";
import { useUserStore, usePermissionStore } from "@/store";
import NProgress from "@/utils/nprogress";
import { RouteRecordRaw } from "vue-router";
import { TOKEN_KEY } from "@/enums/CacheEnum";
export function setupPermission() {
// 白名单路由
@@ -9,7 +10,7 @@ export function setupPermission() {
router.beforeEach(async (to, from, next) => {
NProgress.start();
const hasToken = localStorage.getItem("accessToken");
const hasToken = localStorage.getItem(TOKEN_KEY);
if (hasToken) {
if (to.path === "/login") {
// 如果已登录,跳转首页

View File

@@ -1,7 +1,8 @@
import { RouteRecordRaw } from "vue-router";
import { constantRoutes } from "@/router";
import { store } from "@/store";
import { listRoutes } from "@/api/menu";
import MenuAPI from "@/api/menu";
import { RouteVO } from "@/api/menu/model";
const modules = import.meta.glob("../../views/**/**.vue");
const Layout = () => import("@/layout/index.vue");
@@ -29,25 +30,22 @@ const hasPermission = (roles: string[], route: RouteRecordRaw) => {
};
/**
* 递归过滤有权限的异步(动态)路由
* 递归过滤有权限的动态路由
*
* @param routes 接口返回的异步(动态)路由
* @param routes 接口返回所有的动态路由
* @param roles 用户角色集合
* @returns 返回用户有权限的异步(动态)路由
* @returns 返回用户有权限的动态路由
*/
const filterAsyncRoutes = (routes: RouteRecordRaw[], roles: string[]) => {
const filterAsyncRoutes = (routes: RouteVO[], roles: string[]) => {
const asyncRoutes: RouteRecordRaw[] = [];
routes.forEach((route) => {
const tmpRoute = { ...route }; // ES6扩展运算符复制新对象
if (!route.name) {
tmpRoute.name = route.path;
}
// 判断用户(角色)是否有该路由的访问权限
const tmpRoute = { ...route } as RouteRecordRaw; // 深拷贝 route 对象 避免污染
if (hasPermission(roles, tmpRoute)) {
// 如果是顶级目录,替换为 Layout 组件
if (tmpRoute.component?.toString() == "Layout") {
tmpRoute.component = Layout;
} else {
// 如果是子目录,动态加载组件
const component = modules[`../../views/${tmpRoute.component}.vue`];
if (component) {
tmpRoute.component = component;
@@ -57,7 +55,7 @@ const filterAsyncRoutes = (routes: RouteRecordRaw[], roles: string[]) => {
}
if (tmpRoute.children) {
tmpRoute.children = filterAsyncRoutes(tmpRoute.children, roles);
tmpRoute.children = filterAsyncRoutes(route.children, roles);
}
asyncRoutes.push(tmpRoute);
@@ -66,7 +64,6 @@ const filterAsyncRoutes = (routes: RouteRecordRaw[], roles: string[]) => {
return asyncRoutes;
};
// setup
export const usePermissionStore = defineStore("permission", () => {
// state
@@ -76,6 +73,7 @@ export const usePermissionStore = defineStore("permission", () => {
function setRoutes(newRoutes: RouteRecordRaw[]) {
routes.value = constantRoutes.concat(newRoutes);
}
/**
* 生成动态路由
*
@@ -85,10 +83,10 @@ export const usePermissionStore = defineStore("permission", () => {
function generateRoutes(roles: string[]) {
return new Promise<RouteRecordRaw[]>((resolve, reject) => {
// 接口获取所有路由
listRoutes()
.then(({ data: asyncRoutes }) => {
// 根据角色获取有访问权限的路由
const accessedRoutes = filterAsyncRoutes(asyncRoutes, roles);
MenuAPI.getRoutes()
.then((data) => {
// 过滤有权限的动态路由
const accessedRoutes = filterAsyncRoutes(data, roles);
setRoutes(accessedRoutes);
resolve(accessedRoutes);
})
@@ -97,6 +95,7 @@ export const usePermissionStore = defineStore("permission", () => {
});
});
}
/**
* 获取与激活的顶部菜单项相关的混合模式左侧菜单集合
*/

View File

@@ -1,10 +1,11 @@
import { loginApi, logoutApi } from "@/api/auth";
import { getUserInfoApi } from "@/api/user";
import AuthAPI from "@/api/auth";
import UserAPI from "@/api/user";
import { resetRouter } from "@/router";
import { store } from "@/store";
import { LoginData } from "@/api/auth/types";
import { UserInfo } from "@/api/user/types";
import { LoginData } from "@/api/auth/model";
import { UserInfo } from "@/api/user/model";
import { TOKEN_KEY } from "@/enums/CacheEnum";
export const useUserStore = defineStore("user", () => {
const user = ref<UserInfo>({
@@ -20,10 +21,10 @@ export const useUserStore = defineStore("user", () => {
*/
function login(loginData: LoginData) {
return new Promise<void>((resolve, reject) => {
loginApi(loginData)
.then((response) => {
const { tokenType, accessToken } = response.data;
localStorage.setItem("accessToken", tokenType + " " + accessToken); // Bearer eyJhbGciOiJIUzI1NiJ9.xxx.xxx
AuthAPI.login(loginData)
.then((data) => {
const { tokenType, accessToken } = data;
localStorage.setItem(TOKEN_KEY, tokenType + " " + accessToken); // Bearer eyJhbGciOiJIUzI1NiJ9.xxx.xxx
resolve();
})
.catch((error) => {
@@ -35,8 +36,8 @@ export const useUserStore = defineStore("user", () => {
// 获取信息(用户昵称、头像、角色集合、权限集合)
function getUserInfo() {
return new Promise<UserInfo>((resolve, reject) => {
getUserInfoApi()
.then(({ data }) => {
UserAPI.getInfo()
.then((data) => {
if (!data) {
reject("Verification failed, please Login again.");
return;
@@ -57,9 +58,9 @@ export const useUserStore = defineStore("user", () => {
// user logout
function logout() {
return new Promise<void>((resolve, reject) => {
logoutApi()
AuthAPI.logout()
.then(() => {
localStorage.setItem("accessToken", "");
localStorage.setItem(TOKEN_KEY, "");
location.reload(); // 清空路由
resolve();
})
@@ -73,7 +74,7 @@ export const useUserStore = defineStore("user", () => {
function resetToken() {
console.log("resetToken");
return new Promise<void>((resolve) => {
localStorage.setItem("accessToken", "");
localStorage.setItem(TOKEN_KEY, "");
resetRouter();
resolve();
});

View File

@@ -1,5 +1,7 @@
import axios, { InternalAxiosRequestConfig, AxiosResponse } from "axios";
import { useUserStoreHook } from "@/store/modules/user";
import { ResultEnum } from "@/enums/ResultEnum";
import { TOKEN_KEY } from "@/enums/CacheEnum";
// 创建 axios 实例
const service = axios.create({
@@ -11,7 +13,7 @@ const service = axios.create({
// 请求拦截器
service.interceptors.request.use(
(config: InternalAxiosRequestConfig) => {
const accessToken = localStorage.getItem("accessToken");
const accessToken = localStorage.getItem(TOKEN_KEY);
if (accessToken) {
config.headers.Authorization = accessToken;
}
@@ -25,23 +27,27 @@ service.interceptors.request.use(
// 响应拦截器
service.interceptors.response.use(
(response: AxiosResponse) => {
const { code, msg } = response.data;
if (code === "00000") {
return response.data;
}
// 响应数据为二进制流处理(Excel导出)
if (response.data instanceof ArrayBuffer) {
// 检查配置的响应类型是否为二进制类型('blob' 或 'arraybuffer', 如果是,直接返回响应对象
if (
response.config.responseType === "blob" ||
response.config.responseType === "arraybuffer"
) {
return response;
}
const { code, data, msg } = response.data;
if (code === ResultEnum.SUCCESS) {
return data;
}
ElMessage.error(msg || "系统出错");
return Promise.reject(new Error(msg || "Error"));
},
(error: any) => {
// 异常处理
if (error.response.data) {
const { code, msg } = error.response.data;
// token 过期,重新登录
if (code === "A0230") {
if (code === ResultEnum.TOKEN_INVALID) {
ElMessageBox.confirm("当前页面已失效,请重新登录", "提示", {
confirmButtonText: "确定",
cancelButtonText: "取消",

View File

@@ -1,5 +1,5 @@
import { addUser } from "@/api/user";
import type { UserForm } from "@/api/user/types";
import UserAPI from "@/api/user";
import type { UserForm } from "@/api/user/model";
import type { IModalConfig } from "@/components/PageModal/index.vue";
const modalConfig: IModalConfig<UserForm> = {
@@ -13,7 +13,7 @@ const modalConfig: IModalConfig<UserForm> = {
form: {
labelWidth: 100,
},
formAction: addUser,
formAction: UserAPI.add,
beforeSubmit(data) {
console.log("提交之前处理", data);
},

View File

@@ -1,5 +1,5 @@
import { deleteUsers, exportUser, getUserPage } from "@/api/user";
import type { UserQuery } from "@/api/user/types";
import UserAPI from "@/api/user";
import type { UserQuery } from "@/api/user/model";
import type { IContentConfig } from "@/components/PageContent/index.vue";
const contentConfig: IContentConfig<UserQuery> = {
@@ -15,10 +15,10 @@ const contentConfig: IContentConfig<UserQuery> = {
params.endTime = createAt[1];
delete params.createAt;
}
return getUserPage(params);
return UserAPI.getPage(params);
},
deleteAction: deleteUsers,
exportAction: exportUser,
deleteAction: UserAPI.deleteByIds,
exportAction: UserAPI.export,
pk: "id",
toolbar: [
"refresh",

View File

@@ -1,5 +1,5 @@
import { updateUser } from "@/api/user";
import type { UserForm } from "@/api/user/types";
import UserAPI from "@/api/user";
import type { UserForm } from "@/api/user/model";
import type { IModalConfig } from "@/components/PageModal/index.vue";
const modalConfig: IModalConfig<UserForm> = {
@@ -11,7 +11,7 @@ const modalConfig: IModalConfig<UserForm> = {
appendToBody: true,
},
formAction: function (data) {
return updateUser(data.id as number, data);
return UserAPI.update(data.id as number, data);
},
beforeSubmit(data) {
console.log("提交之前处理", data);

View File

@@ -42,7 +42,7 @@
</template>
<script setup lang="ts">
import { getUserForm } from "@/api/user";
import UserAPI from "@/api/user";
import type { IObject, IOperatData } from "@/hooks/usePage";
import usePage from "@/hooks/usePage";
import addModalConfig from "./config/add";
@@ -65,7 +65,7 @@ const {
// 编辑
async function handleEditClick(row: IObject) {
// 根据id获取数据进行填充
const response = await getUserForm(row.id);
const response = await UserAPI.getFormData(row.id);
editModalRef.value?.setModalVisible(response.data);
}
// 其他工具栏

View File

@@ -4,6 +4,7 @@ import SockJS from "sockjs-client";
import Stomp from "stompjs";
import { useUserStoreHook } from "@/store/modules/user";
import { TOKEN_KEY } from "@/enums/CacheEnum";
const userStore = useUserStoreHook();
@@ -57,7 +58,7 @@ function connectWebSocket() {
stompClient = Stomp.over(socket);
stompClient.connect(
{ Authorization: localStorage.getItem("accessToken") },
{ Authorization: localStorage.getItem(TOKEN_KEY) },
() => {
isConnected.value = true;
messages.value.push({

View File

@@ -115,8 +115,8 @@
<script setup lang="ts">
import { useSettingsStore, useUserStore } from "@/store";
import { getCaptchaApi } from "@/api/auth";
import { LoginData } from "@/api/auth/types";
import AuthAPI from "@/api/auth";
import { LoginData } from "@/api/auth/model";
import { Sunny, Moon } from "@element-plus/icons-vue";
import { LocationQuery, LocationQueryValue, useRoute } from "vue-router";
import router from "@/router";
@@ -175,19 +175,15 @@ const loginRules = computed(() => {
};
});
/**
* 获取验证码
*/
/** 获取验证码 */
function getCaptcha() {
getCaptchaApi().then(({ data }) => {
AuthAPI.getCaptcha().then((data) => {
loginData.value.captchaKey = data.captchaKey;
captchaBase64.value = data.captchaBase64;
});
}
/**
* 登录
*/
/** 登录 */
const route = useRoute();
function handleLogin() {
loginFormRef.value.validate((valid: boolean) => {
@@ -220,19 +216,14 @@ function handleLogin() {
});
}
/**
* 主题切换
*/
/** 主题切换 */
const toggleTheme = () => {
const newTheme =
settingsStore.theme === ThemeEnum.DARK ? ThemeEnum.LIGHT : ThemeEnum.DARK;
settingsStore.changeTheme(newTheme);
};
/**
* 根据屏幕宽度切换设备模式
*/
/** 根据屏幕宽度切换设备模式 */
watchEffect(() => {
if (height.value < 600) {
icpVisible.value = false;
@@ -241,9 +232,7 @@ watchEffect(() => {
}
});
/**
* 检查输入大小写
*/
/** 检查输入大小写 */
function checkCapslock(event: KeyboardEvent) {
// 防止浏览器密码自动填充时报错
if (event instanceof KeyboardEvent) {
@@ -296,3 +285,4 @@ html.dark .login-container {
}
}
</style>
@/api/auth/model

View File

@@ -151,22 +151,14 @@
</template>
<script setup lang="ts">
import {
getDeptForm,
deleteDept,
updateDept,
addDept,
getDeptOptions,
listDepts,
} from "@/api/dept";
import { DeptVO, DeptForm, DeptQuery } from "@/api/dept/types";
defineOptions({
name: "Dept",
inheritAttrs: false,
});
import DeptAPI from "@/api/dept";
import { DeptVO, DeptForm, DeptQuery } from "@/api/dept/model";
const queryFormRef = ref(ElForm);
const deptFormRef = ref(ElForm);
@@ -197,7 +189,7 @@ const rules = reactive({
/** 查询 */
function handleQuery() {
loading.value = true;
listDepts(queryParams).then(({ data }) => {
DeptAPI.getList(queryParams).then((data) => {
deptList.value = data;
loading.value = false;
});
@@ -216,12 +208,12 @@ function handleSelectionChange(selection: any) {
/** 获取部门下拉数据 */
async function loadDeptOptions() {
getDeptOptions().then((response) => {
DeptAPI.getOptions().then((data) => {
deptOptions.value = [
{
value: 0,
label: "顶级部门",
children: response.data,
children: data,
},
];
});
@@ -238,7 +230,7 @@ async function openDialog(parentId?: number, deptId?: number) {
dialog.visible = true;
if (deptId) {
dialog.title = "修改部门";
getDeptForm(deptId).then(({ data }) => {
DeptAPI.getFormData(deptId).then((data) => {
Object.assign(formData, data);
});
} else {
@@ -254,7 +246,7 @@ function handleSubmit() {
const deptId = formData.id;
loading.value = true;
if (deptId) {
updateDept(deptId, formData)
DeptAPI.update(deptId, formData)
.then(() => {
ElMessage.success("修改成功");
closeDialog();
@@ -262,7 +254,7 @@ function handleSubmit() {
})
.finally(() => (loading.value = false));
} else {
addDept(formData)
DeptAPI.update(formData)
.then(() => {
ElMessage.success("新增成功");
closeDialog();
@@ -288,7 +280,7 @@ function handleDelete(deptId?: number) {
cancelButtonText: "取消",
type: "warning",
}).then(() => {
deleteDept(deptIds).then(() => {
DeptAPI.deleteByIds(deptIds).then(() => {
ElMessage.success("删除成功");
resetQuery();
});
@@ -316,3 +308,4 @@ onMounted(() => {
handleQuery();
});
</script>
@/api/dept/model

View File

@@ -129,20 +129,14 @@
</template>
<script setup lang="ts">
import {
getDictPage,
getDictFormData,
addDict,
updateDict,
deleteDict,
} from "@/api/dict";
import { DictPageVO, DictForm, DictQuery } from "@/api/dict/types";
defineOptions({
name: "DictData",
inheritAttrs: false,
});
import DictAPI from "@/api/dict";
import { DictPageVO, DictForm, DictQuery } from "@/api/dict/model";
const props = defineProps({
typeCode: {
type: String,
@@ -198,14 +192,12 @@ const rules = reactive({
value: [{ required: true, message: "请输入字典值", trigger: "blur" }],
});
/**
* 查询
*/
/** 查询 */
function handleQuery() {
if (queryParams.typeCode) {
loading.value = true;
getDictPage(queryParams)
.then(({ data }) => {
DictAPI.getDictPage(queryParams)
.then((data) => {
dictList.value = data.list;
total.value = data.total;
})
@@ -213,9 +205,7 @@ function handleQuery() {
}
}
/**
* 重置查询
*/
/** 重置查询 */
function resetQuery() {
queryFormRef.value.resetFields();
queryParams.pageNum = 1;
@@ -240,7 +230,7 @@ function openDialog(dictId?: number) {
dialog.visible = true;
if (dictId) {
dialog.title = "修改字典";
getDictFormData(dictId).then(({ data }) => {
DictAPI.getDictFormData(dictId).then((data) => {
Object.assign(formData, data);
});
} else {
@@ -248,16 +238,14 @@ function openDialog(dictId?: number) {
}
}
/**
* 字典表单提交
*/
/** 字典表单提交 */
function handleSubmit() {
dataFormRef.value.validate((isValid: boolean) => {
if (isValid) {
loading.value = false;
const dictId = formData.id;
if (dictId) {
updateDict(dictId, formData)
DictAPI.updateDict(dictId, formData)
.then(() => {
ElMessage.success("修改成功");
closeDialog();
@@ -265,7 +253,7 @@ function handleSubmit() {
})
.finally(() => (loading.value = false));
} else {
addDict(formData)
DictAPI.addDict(formData)
.then(() => {
ElMessage.success("新增成功");
closeDialog();
@@ -277,17 +265,13 @@ function handleSubmit() {
});
}
/**
* 关闭弹窗
*/
/** 关闭弹窗 */
function closeDialog() {
dialog.visible = false;
resetForm();
}
/**
* 重置表单
*/
/** 重置表单 */
function resetForm() {
dataFormRef.value.resetFields();
dataFormRef.value.clearValidate();
@@ -298,9 +282,7 @@ function resetForm() {
formData.typeCode = props.typeCode;
}
/**
* 删除字典
*/
/** 删除字典 */
function handleDelete(dictId?: number) {
const dictIds = [dictId || ids.value].join(",");
if (!dictIds) {
@@ -313,7 +295,7 @@ function handleDelete(dictId?: number) {
cancelButtonText: "取消",
type: "warning",
}).then(() => {
deleteDict(dictIds).then(() => {
DictAPI.deleteDictByIds(dictIds).then(() => {
ElMessage.success("删除成功");
resetQuery();
});
@@ -324,3 +306,4 @@ onMounted(() => {
handleQuery();
});
</script>
@/api/dict/model

View File

@@ -148,21 +148,15 @@
</template>
<script setup lang="ts">
import {
getDictTypePage,
getDictTypeForm,
addDictType,
updateDictType,
deleteDictTypes,
} from "@/api/dict";
import { DictTypePageVO, DictTypeQuery, DictTypeForm } from "@/api/dict/types";
defineOptions({
name: "DictType",
inheritAttrs: false,
});
import DictAPI from "@/api/dict";
import { DictTypePageVO, DictTypeQuery, DictTypeForm } from "@/api/dict/model";
const queryFormRef = ref(ElForm);
const dataFormRef = ref(ElForm);
@@ -194,8 +188,8 @@ const rules = reactive({
/** 查询 */
function handleQuery() {
loading.value = true;
getDictTypePage(queryParams)
.then(({ data }) => {
DictAPI.getDictTypePage(queryParams)
.then((data) => {
dictTypeList.value = data.list;
total.value = data.total;
})
@@ -227,7 +221,7 @@ function openDialog(dicTypeId?: number) {
dialog.visible = true;
if (dicTypeId) {
dialog.title = "修改字典类型";
getDictTypeForm(dicTypeId).then(({ data }) => {
DictAPI.getDictTypeForm(dicTypeId).then((data) => {
Object.assign(formData, data);
});
} else {
@@ -242,7 +236,7 @@ function handleSubmit() {
loading.value = false;
const dictTypeId = formData.id;
if (dictTypeId) {
updateDictType(dictTypeId, formData)
DictAPI.updateDictType(dictTypeId, formData)
.then(() => {
ElMessage.success("修改成功");
closeDialog();
@@ -250,7 +244,7 @@ function handleSubmit() {
})
.finally(() => (loading.value = false));
} else {
addDictType(formData)
DictAPI.addDictType(formData)
.then(() => {
ElMessage.success("新增成功");
closeDialog();
@@ -290,7 +284,7 @@ function handleDelete(dictTypeId?: number) {
cancelButtonText: "取消",
type: "warning",
}).then(() => {
deleteDictTypes(dictTypeIds).then(() => {
DictAPI.deleteDictTypes(dictTypeIds).then(() => {
ElMessage.success("删除成功");
resetQuery();
});
@@ -322,3 +316,4 @@ onMounted(() => {
handleQuery();
});
</script>
@/api/dict/model

View File

@@ -312,21 +312,12 @@
<script setup lang="ts">
defineOptions({
// eslint-disable-next-line vue/no-reserved-component-names
name: "Menu",
inheritAttrs: false,
});
import { MenuQuery, MenuForm, MenuVO } from "@/api/menu/types";
import {
listMenus,
getMenuForm,
getMenuOptions,
addMenu,
deleteMenu,
updateMenu,
} from "@/api/menu";
import MenuAPI from "@/api/menu";
import { MenuQuery, MenuForm, MenuVO } from "@/api/menu/model";
import { MenuTypeEnum } from "@/enums/MenuTypeEnum";
const queryFormRef = ref(ElForm);
@@ -376,8 +367,8 @@ const menuCacheData = reactive({
function handleQuery() {
// 重置父组件
loading.value = true;
listMenus(queryParams)
.then(({ data }) => {
MenuAPI.getList(queryParams)
.then((data) => {
menuList.value = data;
})
.then(() => {
@@ -403,15 +394,15 @@ function onRowClick(row: MenuVO) {
* @param menuId 菜单ID
*/
function openDialog(parentId?: number, menuId?: number) {
getMenuOptions()
.then(({ data }) => {
MenuAPI.getOptions()
.then((data) => {
menuOptions.value = [{ value: 0, label: "顶级菜单", children: data }];
})
.then(() => {
dialog.visible = true;
if (menuId) {
dialog.title = "编辑菜单";
getMenuForm(menuId).then(({ data }) => {
MenuAPI.getFormData(menuId).then((data) => {
Object.assign(formData, data);
menuCacheData.type = data.type;
menuCacheData.path = data.path ?? "";
@@ -439,13 +430,13 @@ function submitForm() {
if (isValid) {
const menuId = formData.id;
if (menuId) {
updateMenu(menuId, formData).then(() => {
MenuAPI.update(menuId, formData).then(() => {
ElMessage.success("修改成功");
closeDialog();
handleQuery();
});
} else {
addMenu(formData).then(() => {
MenuAPI.add(formData).then(() => {
ElMessage.success("新增成功");
closeDialog();
handleQuery();
@@ -468,7 +459,7 @@ function handleDelete(menuId: number) {
type: "warning",
})
.then(() => {
deleteMenu(menuId).then(() => {
MenuAPI.deleteById(menuId).then(() => {
ElMessage.success("删除成功");
handleQuery();
});
@@ -503,3 +494,4 @@ onMounted(() => {
handleQuery();
});
</script>
@/api/menu/model

View File

@@ -181,18 +181,10 @@
</template>
<script setup lang="ts">
import {
getRolePage,
updateRole,
getRoleForm,
addRole,
deleteRoles,
getRoleMenuIds,
updateRoleMenus,
} from "@/api/role";
import { getMenuOptions } from "@/api/menu";
import RoleAPI from "@/api/role";
import MenuAPI from "@/api/menu";
import { RolePageVO, RoleForm, RoleQuery } from "@/api/role/types";
import { RolePageVO, RoleForm, RoleQuery } from "@/api/role/model";
defineOptions({
name: "Role",
@@ -246,8 +238,8 @@ let checkedRole: CheckedRole = reactive({});
/** 查询 */
function handleQuery() {
loading.value = true;
getRolePage(queryParams)
.then(({ data }) => {
RoleAPI.getPage(queryParams)
.then((data) => {
roleList.value = data.list;
total.value = data.total;
})
@@ -272,7 +264,7 @@ function openDialog(roleId?: number) {
dialog.visible = true;
if (roleId) {
dialog.title = "修改角色";
getRoleForm(roleId).then(({ data }) => {
RoleAPI.getFormData(roleId).then((data) => {
Object.assign(formData, data);
});
} else {
@@ -287,7 +279,7 @@ function handleSubmit() {
loading.value = true;
const roleId = formData.id;
if (roleId) {
updateRole(roleId, formData)
RoleAPI.update(roleId, formData)
.then(() => {
ElMessage.success("修改成功");
closeDialog();
@@ -295,7 +287,7 @@ function handleSubmit() {
})
.finally(() => (loading.value = false));
} else {
addRole(formData)
RoleAPI.add(formData)
.then(() => {
ElMessage.success("新增成功");
closeDialog();
@@ -337,7 +329,7 @@ function handleDelete(roleId?: number) {
type: "warning",
}).then(() => {
loading.value = true;
deleteRoles(roleIds)
RoleAPI.deleteByIds(roleIds)
.then(() => {
ElMessage.success("删除成功");
resetQuery();
@@ -347,7 +339,7 @@ function handleDelete(roleId?: number) {
}
/** 打开分配菜单弹窗 */
function openMenuDialog(row: RolePageVO) {
async function openMenuDialog(row: RolePageVO) {
const roleId = row.id;
if (roleId) {
checkedRole = {
@@ -358,20 +350,19 @@ function openMenuDialog(row: RolePageVO) {
loading.value = true;
// 获取所有的菜单
getMenuOptions().then((response) => {
menuList.value = response.data;
// 回显角色已拥有的菜单
getRoleMenuIds(roleId)
.then(({ data }) => {
const checkedMenuIds = data;
checkedMenuIds.forEach((menuId) =>
menuRef.value.setChecked(menuId, true, false)
);
})
.finally(() => {
loading.value = false;
});
});
menuList.value = await MenuAPI.getOptions();
// 回显角色已拥有的菜单
RoleAPI.getRoleMenuIds(roleId)
.then((data) => {
const checkedMenuIds = data;
checkedMenuIds.forEach((menuId) =>
menuRef.value.setChecked(menuId, true, false)
);
})
.finally(() => {
loading.value = false;
});
}
}
@@ -384,7 +375,7 @@ function handleRoleMenuSubmit() {
.map((node: any) => node.value);
loading.value = true;
updateRoleMenus(roleId, checkedMenuIds)
RoleAPI.updateRoleMenus(roleId, checkedMenuIds)
.then(() => {
ElMessage.success("分配权限成功");
menuDialogVisible.value = false;
@@ -400,3 +391,4 @@ onMounted(() => {
handleQuery();
});
</script>
@/api/role/model

View File

@@ -21,8 +21,7 @@
</template>
<script setup lang="ts">
import { getDeptOptions } from "@/api/dept";
import DeptAPI from "@/api/dept";
const props = defineProps({
modelValue: {
type: [Number],
@@ -62,8 +61,8 @@ function handleNodeClick(data: { [key: string]: any }) {
}
onBeforeMount(() => {
getDeptOptions().then((response) => {
deptList.value = response.data;
DeptAPI.getOptions().then((data) => {
deptList.value = data;
});
});
</script>

View File

@@ -332,21 +332,11 @@ defineOptions({
inheritAttrs: false,
});
import {
getUserPage,
getUserForm,
deleteUsers,
addUser,
updateUser,
updateUserPassword,
downloadTemplateApi,
exportUser,
importUser,
} from "@/api/user";
import { getDeptOptions } from "@/api/dept";
import { getRoleOptions } from "@/api/role";
import UserAPI from "@/api/user";
import DeptAPI from "@/api/dept";
import RoleAPI from "@/api/role";
import { UserForm, UserQuery, UserPageVO } from "@/api/user/types";
import { UserForm, UserQuery, UserPageVO } from "@/api/user/model";
import type { UploadInstance } from "element-plus";
import { genFileId } from "element-plus";
@@ -418,8 +408,9 @@ const rules = reactive({
/** 查询 */
function handleQuery() {
loading.value = true;
getUserPage(queryParams)
.then(({ data }) => {
UserAPI.getPage(queryParams)
.then((data) => {
console.log("handleQuery", data);
pageData.value = data.list;
total.value = data.total;
})
@@ -458,7 +449,7 @@ function resetPassword(row: { [key: string]: any }) {
ElMessage.warning("请输入新密码");
return false;
}
updateUserPassword(row.id, value).then(() => {
UserAPI.updatePassword(row.id, value).then(() => {
ElMessage.success("密码重置成功,新密码是:" + value);
});
});
@@ -466,15 +457,15 @@ function resetPassword(row: { [key: string]: any }) {
/** 加载角色下拉数据源 */
async function loadRoleOptions() {
getRoleOptions().then((response) => {
roleList.value = response.data;
RoleAPI.getOptions().then((data) => {
roleList.value = data;
});
}
/** 加载部门下拉数据源 */
async function loadDeptOptions() {
getDeptOptions().then((response) => {
deptList.value = response.data;
DeptAPI.getOptions().then((data) => {
deptList.value = data;
});
}
@@ -494,7 +485,7 @@ async function openDialog(type: string, id?: number) {
await loadRoleOptions();
if (id) {
dialog.title = "修改用户";
getUserForm(id).then(({ data }) => {
UserAPI.getFormData(id).then((data) => {
Object.assign(formData, { ...data });
});
} else {
@@ -535,7 +526,7 @@ const handleSubmit = useThrottleFn(() => {
const userId = formData.id;
loading.value = true;
if (userId) {
updateUser(userId, formData)
UserAPI.update(userId, formData)
.then(() => {
ElMessage.success("修改用户成功");
closeDialog();
@@ -543,7 +534,7 @@ const handleSubmit = useThrottleFn(() => {
})
.finally(() => (loading.value = false));
} else {
addUser(formData)
UserAPI.add(formData)
.then(() => {
ElMessage.success("新增用户成功");
closeDialog();
@@ -562,8 +553,8 @@ const handleSubmit = useThrottleFn(() => {
ElMessage.warning("上传Excel文件不能为空");
return false;
}
importUser(importData?.deptId, importData?.file).then((response) => {
ElMessage.success(response.data);
UserAPI.import(importData?.deptId, importData?.file).then((data) => {
ElMessage.success("导入用户成功");
closeDialog();
resetQuery();
});
@@ -583,7 +574,7 @@ function handleDelete(id?: number) {
cancelButtonText: "取消",
type: "warning",
}).then(function () {
deleteUsers(userIds).then(() => {
UserAPI.deleteByIds(userIds).then(() => {
ElMessage.success("删除成功");
resetQuery();
});
@@ -592,7 +583,7 @@ function handleDelete(id?: number) {
/** 下载导入模板 */
function downloadTemplate() {
downloadTemplateApi().then((response: any) => {
UserAPI.downloadTemplate().then((response: any) => {
const fileData = response.data;
const fileName = decodeURI(
response.headers["content-disposition"].split(";")[1].split("=")[1]
@@ -631,7 +622,7 @@ function handleFileExceed(files: any) {
/** 导出用户 */
function handleExport() {
exportUser(queryParams).then((response: any) => {
UserAPI.export(queryParams).then((response: any) => {
const fileData = response.data;
const fileName = decodeURI(
response.headers["content-disposition"].split(";")[1].split("=")[1]