From 52be26b37175a4be71d28751b94be23e203741ec Mon Sep 17 00:00:00 2001 From: mldong Date: Mon, 21 Oct 2024 20:52:22 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E8=B7=AF=E7=94=B1=E5=A2=9E=E5=8A=A0per?= =?UTF-8?q?ms=E9=85=8D=E7=BD=AE=E9=A1=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- apps/web-antd/src/router/guard.ts | 1 + apps/web-ele/src/router/guard.ts | 1 + apps/web-naive/src/router/guard.ts | 1 + packages/@core/base/typings/src/vue-router.d.ts | 5 +++++ packages/effects/access/src/accessible.ts | 3 ++- .../src/helpers/generate-routes-frontend.ts | 17 +++++++++++++++++ 6 files changed, 27 insertions(+), 1 deletion(-) diff --git a/apps/web-antd/src/router/guard.ts b/apps/web-antd/src/router/guard.ts index 205ee5695..589b54054 100644 --- a/apps/web-antd/src/router/guard.ts +++ b/apps/web-antd/src/router/guard.ts @@ -102,6 +102,7 @@ function setupAccessGuard(router: Router) { // 生成菜单和路由 const { accessibleMenus, accessibleRoutes } = await generateAccess({ + accessCodes: accessStore.accessCodes || [], roles: userRoles, router, // 则会在菜单中显示,但是访问会被重定向到403 diff --git a/apps/web-ele/src/router/guard.ts b/apps/web-ele/src/router/guard.ts index 205ee5695..589b54054 100644 --- a/apps/web-ele/src/router/guard.ts +++ b/apps/web-ele/src/router/guard.ts @@ -102,6 +102,7 @@ function setupAccessGuard(router: Router) { // 生成菜单和路由 const { accessibleMenus, accessibleRoutes } = await generateAccess({ + accessCodes: accessStore.accessCodes || [], roles: userRoles, router, // 则会在菜单中显示,但是访问会被重定向到403 diff --git a/apps/web-naive/src/router/guard.ts b/apps/web-naive/src/router/guard.ts index 6c9f8232a..3e05137a2 100644 --- a/apps/web-naive/src/router/guard.ts +++ b/apps/web-naive/src/router/guard.ts @@ -101,6 +101,7 @@ function setupAccessGuard(router: Router) { // 生成菜单和路由 const { accessibleMenus, accessibleRoutes } = await generateAccess({ + accessCodes: accessStore.accessCodes || [], roles: userRoles, router, // 则会在菜单中显示,但是访问会被重定向到403 diff --git a/packages/@core/base/typings/src/vue-router.d.ts b/packages/@core/base/typings/src/vue-router.d.ts index 534358ccd..726af723c 100644 --- a/packages/@core/base/typings/src/vue-router.d.ts +++ b/packages/@core/base/typings/src/vue-router.d.ts @@ -102,6 +102,10 @@ interface RouteMeta { * 用于路由->菜单排序 */ order?: number; + /** + * 需要特定的权限码标识才可以访问 + */ + perms?: string[]; /** * 菜单所携带的参数 */ @@ -121,6 +125,7 @@ type RouteRecordStringComponent = { type ComponentRecordType = Record Promise>; interface GenerateMenuAndRoutesOptions { + accessCodes?: string[]; fetchMenuListAsync?: () => Promise; forbiddenComponent?: RouteRecordRaw['component']; layoutMap?: ComponentRecordType; diff --git a/packages/effects/access/src/accessible.ts b/packages/effects/access/src/accessible.ts index c951d92a5..e80b2c7f0 100644 --- a/packages/effects/access/src/accessible.ts +++ b/packages/effects/access/src/accessible.ts @@ -42,7 +42,7 @@ async function generateRoutes( mode: AccessModeType, options: GenerateMenuAndRoutesOptions, ) { - const { forbiddenComponent, roles, routes } = options; + const { forbiddenComponent, roles, routes, accessCodes } = options; let resultRoutes: RouteRecordRaw[] = routes; switch (mode) { @@ -54,6 +54,7 @@ async function generateRoutes( resultRoutes = await generateRoutesByFrontend( routes, roles || [], + accessCodes || [], forbiddenComponent, ); break; diff --git a/packages/utils/src/helpers/generate-routes-frontend.ts b/packages/utils/src/helpers/generate-routes-frontend.ts index dafc8a7d3..5e20da865 100644 --- a/packages/utils/src/helpers/generate-routes-frontend.ts +++ b/packages/utils/src/helpers/generate-routes-frontend.ts @@ -8,10 +8,14 @@ import { filterTree, mapTree } from '@vben-core/shared/utils'; async function generateRoutesByFrontend( routes: RouteRecordRaw[], roles: string[], + accessCodes: string[], forbiddenComponent?: RouteRecordRaw['component'], ): Promise { // 根据角色标识过滤路由表,判断当前用户是否拥有指定权限 const finalRoutes = filterTree(routes, (route) => { + if (!route.meta?.authority) { + return hasPerms(route, accessCodes); + } return hasAuthority(route, roles); }); @@ -42,7 +46,20 @@ function hasAuthority(route: RouteRecordRaw, access: string[]) { return canAccess || (!canAccess && menuHasVisibleWithForbidden(route)); } +/** + * 判断路由是否有权限访问 + * @param route + * @param access + */ +function hasPerms(route: RouteRecordRaw, access: string[]) { + const perms = route.meta?.perms; + if (!perms) { + return true; + } + const canAccess = access.some((value) => perms.includes(value)); + return canAccess || (!canAccess && menuHasVisibleWithForbidden(route)); +} /** * 判断路由是否在菜单中显示,但是访问会被重定向到403 * @param route