From 8a4e98193105dca85f61b8e290e6178a3fc522bb Mon Sep 17 00:00:00 2001 From: xiaojunnuo Date: Sat, 28 Feb 2026 12:13:31 +0800 Subject: [PATCH] chore: project detail join approve --- packages/ui/certd-client/src/api/service.ts | 2 +- .../src/components/project-selector/index.vue | 13 ++ .../src/locales/langs/en-US/certd.ts | 3 + .../src/locales/langs/zh-CN/certd.ts | 3 + .../src/plugin/fast-crud/index.tsx | 1 - .../plugin/permission/use-crud-permission.ts | 2 + .../src/router/source/modules/certd.ts | 10 +- .../certd-client/src/store/project/index.ts | 7 +- .../ui/certd-client/src/views/certd/dicts.ts | 11 +- .../src/views/certd/project/detail/api.ts | 12 +- .../src/views/certd/project/detail/crud.tsx | 58 +++++++-- .../src/views/certd/project/detail/index.vue | 48 +++++++- .../src/views/certd/project/detail/use.ts | 46 +++++++ .../src/views/certd/project/join.vue | 18 +-- .../controller/user/basic/user-controller.ts | 60 +++++++++ .../user/enterprise/project-controller.ts | 12 ++ .../enterprise/project-member-controller.ts | 115 ++++++++++++++++++ .../service/project-member-service.ts | 3 +- .../sys/enterprise/service/project-service.ts | 97 +++++++++------ 19 files changed, 449 insertions(+), 72 deletions(-) create mode 100644 packages/ui/certd-client/src/views/certd/project/detail/use.ts create mode 100644 packages/ui/certd-server/src/controller/user/basic/user-controller.ts create mode 100644 packages/ui/certd-server/src/controller/user/enterprise/project-member-controller.ts diff --git a/packages/ui/certd-client/src/api/service.ts b/packages/ui/certd-client/src/api/service.ts index 02b4a99df..e42647448 100644 --- a/packages/ui/certd-client/src/api/service.ts +++ b/packages/ui/certd-client/src/api/service.ts @@ -156,7 +156,7 @@ function createRequestFunction(service: any) { Object.assign(configDefault, config); if (projectStore.isEnterprise && !config.url.startsWith("/sys") && !config.url.startsWith("http")) { - configDefault.params.projectId = projectStore.currentProjectId; + configDefault.params.projectId = projectStore.currentProject?.id; } return service(configDefault); }; diff --git a/packages/ui/certd-client/src/components/project-selector/index.vue b/packages/ui/certd-client/src/components/project-selector/index.vue index b9f53a837..1d6a30bd0 100644 --- a/packages/ui/certd-client/src/components/project-selector/index.vue +++ b/packages/ui/certd-client/src/components/project-selector/index.vue @@ -8,6 +8,12 @@ + +
+ + 加入其他项目 +
+
@@ -22,6 +28,7 @@ import { computed, onMounted } from "vue"; import { useProjectStore } from "/@/store/project"; import { useDicts } from "/@/views/certd/dicts"; +import { useRouter } from "vue-router"; defineOptions({ name: "ProjectSelector", }); @@ -32,7 +39,13 @@ onMounted(async () => { console.log(projectStore.myProjects); }); +const router = useRouter(); function handleMenuClick({ key }: any) { + if (key === "join") { + router.push("/certd/project/join"); + return; + } + projectStore.changeCurrentProject(key); window.location.reload(); } diff --git a/packages/ui/certd-client/src/locales/langs/en-US/certd.ts b/packages/ui/certd-client/src/locales/langs/en-US/certd.ts index 5d56e96cb..dcf00ef08 100644 --- a/packages/ui/certd-client/src/locales/langs/en-US/certd.ts +++ b/packages/ui/certd-client/src/locales/langs/en-US/certd.ts @@ -820,6 +820,7 @@ export default { write: "Write", admin: "Admin", }, + projectMemberStatus: "Member Status", }, project: { noProjectJoined: "You haven't joined any projects yet", @@ -834,6 +835,8 @@ export default { leave: "Leave Project", leaveSuccess: "Leave project successful", leaveFailed: "Leave project failed, please try again later", + applyJoinConfirm: "Are you sure you want to apply to join this project?", + leaveConfirm: "Are you sure you want to leave this project?", }, addonSelector: { select: "Select", diff --git a/packages/ui/certd-client/src/locales/langs/zh-CN/certd.ts b/packages/ui/certd-client/src/locales/langs/zh-CN/certd.ts index 1d2d8b819..23e7416fe 100644 --- a/packages/ui/certd-client/src/locales/langs/zh-CN/certd.ts +++ b/packages/ui/certd-client/src/locales/langs/zh-CN/certd.ts @@ -836,6 +836,7 @@ export default { write: "写入", admin: "管理员", }, + projectMemberStatus: "成员状态", }, project: { noProjectJoined: "您还没有加入任何项目", @@ -850,5 +851,7 @@ export default { leave: "退出项目", leaveSuccess: "退出项目成功", leaveFailed: "退出项目失败,请稍后重试", + applyJoinConfirm: "确认加入项目?", + leaveConfirm: "确认退出项目?", }, }; diff --git a/packages/ui/certd-client/src/plugin/fast-crud/index.tsx b/packages/ui/certd-client/src/plugin/fast-crud/index.tsx index 50922a486..0ffd43247 100644 --- a/packages/ui/certd-client/src/plugin/fast-crud/index.tsx +++ b/packages/ui/certd-client/src/plugin/fast-crud/index.tsx @@ -123,7 +123,6 @@ function install(app: App, options: any = {}) { if (scope.key === "__blank__") { return false; } - //不能用 !scope.value , 否则switch组件设置为关之后就消失了 const { value, key, props } = scope; return !value && key != "_index" && value != false && value != 0; diff --git a/packages/ui/certd-client/src/plugin/permission/use-crud-permission.ts b/packages/ui/certd-client/src/plugin/permission/use-crud-permission.ts index 315e21ccd..964921ee2 100644 --- a/packages/ui/certd-client/src/plugin/permission/use-crud-permission.ts +++ b/packages/ui/certd-client/src/plugin/permission/use-crud-permission.ts @@ -82,6 +82,7 @@ export function useCrudPermission({ permission }: UseCrudPermissionProps) { if (isProjectPermission) { removePermission = per.projectPermission || "write"; } + debugger; return LodashMerge( { actionbar: { @@ -94,6 +95,7 @@ export function useCrudPermission({ permission }: UseCrudPermissionProps) { edit: { show: hasActionPermission(editPermission) }, remove: { show: hasActionPermission(removePermission) }, view: { show: hasActionPermission(viewPermission) }, + copy: { show: hasActionPermission(addPermission) }, }, }, }, diff --git a/packages/ui/certd-client/src/router/source/modules/certd.ts b/packages/ui/certd-client/src/router/source/modules/certd.ts index 990aac7eb..f5a4681f6 100644 --- a/packages/ui/certd-client/src/router/source/modules/certd.ts +++ b/packages/ui/certd-client/src/router/source/modules/certd.ts @@ -25,8 +25,8 @@ export const certdResources = [ const projectStore = useProjectStore(); return projectStore.isEnterprise; }, + isMenu: false, icon: "ion:apps", - permission: "sys:settings:edit", keepAlive: true, }, }, @@ -36,10 +36,12 @@ export const certdResources = [ path: "/certd/project/detail", component: "/certd/project/detail/index.vue", meta: { - isMenu: false, - show: true, + show: () => { + const projectStore = useProjectStore(); + return projectStore.isEnterprise; + }, + isMenu: true, icon: "ion:apps", - permission: "sys:settings:edit", }, }, { diff --git a/packages/ui/certd-client/src/store/project/index.ts b/packages/ui/certd-client/src/store/project/index.ts index 68d656524..0627f8420 100644 --- a/packages/ui/certd-client/src/store/project/index.ts +++ b/packages/ui/certd-client/src/store/project/index.ts @@ -4,6 +4,7 @@ import { message } from "ant-design-vue"; import { computed, ref } from "vue"; import { useSettingStore } from "../settings"; import { LocalStorage } from "/@/utils/util.storage"; +import { useUserStore } from "../user"; export type ProjectItem = { id: string; @@ -14,7 +15,9 @@ export type ProjectItem = { export const useProjectStore = defineStore("app.project", () => { const myProjects = ref([]); const inited = ref(false); - const lastProjectId = LocalStorage.get("currentProjectId"); + const userStore = useUserStore(); + const userId = userStore.getUserInfo?.id; + const lastProjectId = LocalStorage.get("currentProjectId:" + userId); const currentProjectId = ref(lastProjectId); // 直接调用 const projects = computed(() => { @@ -67,13 +70,11 @@ export const useProjectStore = defineStore("app.project", () => { } async function reload() { - debugger; inited.value = false; await init(); } async function init() { - debugger; if (!inited.value) { await loadMyProjects(); inited.value = true; diff --git a/packages/ui/certd-client/src/views/certd/dicts.ts b/packages/ui/certd-client/src/views/certd/dicts.ts index 3ce74fa29..f80f4754f 100644 --- a/packages/ui/certd-client/src/views/certd/dicts.ts +++ b/packages/ui/certd-client/src/views/certd/dicts.ts @@ -1,5 +1,6 @@ import { dict } from "@fast-crud/fast-crud"; import { GetMyProjectList } from "./project/api"; +import { request } from "/@/api/service"; const projectPermissionDict = dict({ data: [ @@ -65,8 +66,16 @@ const myProjectDict = dict({ }); const userDict = dict({ - url: "/sys/authority/user/getSimpleUsers", + url: "/basic/user/getSimpleUsers", value: "id", + getData: async () => { + const res = await request({ + url: "/basic/user/getSimpleUsers", + method: "POST", + }); + return res; + }, + immediate: false, onReady: ({ dict }) => { for (const item of dict.data) { item.label = item.nickName || item.username || item.phoneCode + item.mobile; diff --git a/packages/ui/certd-client/src/views/certd/project/detail/api.ts b/packages/ui/certd-client/src/views/certd/project/detail/api.ts index e62684eab..b1cdf8646 100644 --- a/packages/ui/certd-client/src/views/certd/project/detail/api.ts +++ b/packages/ui/certd-client/src/views/certd/project/detail/api.ts @@ -1,6 +1,6 @@ import { request } from "/src/api/service"; -const apiPrefix = "/enterprise/myProjectMember"; +const apiPrefix = "/enterprise/projectMember"; const userApiPrefix = "/sys/authority/user"; export async function GetList(query: any) { return await request({ @@ -65,3 +65,13 @@ export async function GetUserSimpleByIds(query: any) { data: query, }); } + +export async function ApproveJoin(id: any) { + return await request({ + url: "/enterprise/project/approveJoin", + method: "post", + data: { + id, + }, + }); +} diff --git a/packages/ui/certd-client/src/views/certd/project/detail/crud.tsx b/packages/ui/certd-client/src/views/certd/project/detail/crud.tsx index 556336e92..67a7a300c 100644 --- a/packages/ui/certd-client/src/views/certd/project/detail/crud.tsx +++ b/packages/ui/certd-client/src/views/certd/project/detail/crud.tsx @@ -7,6 +7,7 @@ import { useSettingStore } from "/@/store/settings"; import { useUserStore } from "/@/store/user"; import { useI18n } from "/src/locales"; import { useDicts } from "../../dicts"; +import { useApprove } from "./use"; export default function ({ crudExpose, context }: CreateCrudOptionsProps): CreateCrudOptionsRet { const router = useRouter(); @@ -34,8 +35,9 @@ export default function ({ crudExpose, context }: CreateCrudOptionsProps): Creat const settingStore = useSettingStore(); const selectedRowKeys: Ref = ref([]); context.selectedRowKeys = selectedRowKeys; - - const { userDict } = useDicts(); + const { hasActionPermission } = context; + const { userDict, projectMemberStatusDict, projectPermissionDict } = useDicts(); + const { openApproveDialog } = useApprove(); return { crudOptions: { @@ -118,13 +120,7 @@ export default function ({ crudExpose, context }: CreateCrudOptionsProps): Creat permission: { title: t("certd.ent.projectPermission"), type: "dict-select", - dict: dict({ - data: [ - { label: t("certd.ent.permission.read"), value: "read", color: "cyan" }, - { label: t("certd.ent.permission.write"), value: "write", color: "blue" }, - { label: t("certd.ent.permission.admin"), value: "admin", color: "green" }, - ], - }), + dict: projectPermissionDict, search: { show: true, }, @@ -135,6 +131,50 @@ export default function ({ crudExpose, context }: CreateCrudOptionsProps): Creat width: 200, }, }, + status: { + title: t("certd.ent.projectMemberStatus"), + type: "dict-select", + dict: projectMemberStatusDict, + search: { + show: true, + }, + form: { + show: true, + }, + column: { + width: 200, + cellRender: ({ row }) => { + let approveButton: any = ""; + if (row.status === "pending" && hasActionPermission("admin")) { + approveButton = ( + { + openApproveDialog({ + id: row.id, + permission: row.permission, + onSubmit: async (form: any) => { + await api.ApproveJoin(form); + crudExpose.doRefresh(); + }, + }); + }} + > + 审批 + + ); + } + return ( +
+ + {approveButton} +
+ ); + }, + }, + }, createTime: { title: t("certd.createTime"), type: "datetime", diff --git a/packages/ui/certd-client/src/views/certd/project/detail/index.vue b/packages/ui/certd-client/src/views/certd/project/detail/index.vue index 84f8e6d3e..b122634cd 100644 --- a/packages/ui/certd-client/src/views/certd/project/detail/index.vue +++ b/packages/ui/certd-client/src/views/certd/project/detail/index.vue @@ -3,8 +3,14 @@ @@ -19,13 +25,17 @@