diff --git a/src/App.tsx b/src/App.tsx index 3b7738a..dd4f9cf 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,13 +1,27 @@ import React from 'react' -import router from '@/router' +import { getRouter } from '@/router' import LoadingMask from '@/components/common/LoadingMask' +export const AppContext = createContext<{ refreshRouter: () => void }>({ + refreshRouter: () => undefined +}) + const App: React.FC = () => { + const [routerState, setRouterState] = useState(getRouter) + return ( <> - }> - - + { + setRouterState(getRouter()) + } + }} + > + }> + + + ) } diff --git a/src/AuthRoute.tsx b/src/AuthRoute.tsx index dcf5b83..4fe0f43 100644 --- a/src/AuthRoute.tsx +++ b/src/AuthRoute.tsx @@ -22,8 +22,13 @@ const AuthRoute = () => { ) } if (isLogin && lastMatch.pathname === '/login') { - return + return } + + if (location.pathname.length > 1 && location.pathname.endsWith('/')) { + return + } + return outlet }, [ handle?.title, diff --git a/src/pages/HomeFramework.tsx b/src/pages/HomeFramework.tsx index e174f00..327f1f3 100644 --- a/src/pages/HomeFramework.tsx +++ b/src/pages/HomeFramework.tsx @@ -2,7 +2,7 @@ import React from 'react' import Icon from '@ant-design/icons' import '@/assets/css/pages/home-framework.scss' import { COLOR_FONT_SECONDARY } from '@/constants/common.constants' -import router from '@/router' +import { getRouter } from '@/router' import LoadingMask from '@/components/common/LoadingMask' import HideScrollbar, { HideScrollbarElement } from '@/components/common/HideScrollbar' @@ -54,7 +54,8 @@ export const HomeFrameworkContext = createContext<{ const HomeFramework: React.FC = () => { const routeId = useMatches()[1].id - const routeChildren = router.routes[0].children?.find((value) => value.id === routeId)?.children + const routeChildren = getRouter().routes[0].children?.find((value) => value.id === routeId) + ?.children const pathname = useLocation().pathname diff --git a/src/pages/Login.tsx b/src/pages/Login.tsx index 4fd39b2..197eea6 100644 --- a/src/pages/Login.tsx +++ b/src/pages/Login.tsx @@ -8,8 +8,10 @@ import { } from '@/constants/common.constants' import { utcToLocalTime } from '@/util/datetime' import { getUserInfo, login, setToken } from '@/util/auth' +import { AppContext } from '@/App' const Login: React.FC = () => { + const { refreshRouter } = useContext(AppContext) const [messageApi, contextHolder] = message.useMessage() const navigate = useNavigate() const [searchParams] = useSearchParams() @@ -32,6 +34,7 @@ const Login: React.FC = () => { navigate('/') } void getUserInfo().then((user) => { + refreshRouter() notification.success({ message: '欢迎回来', description: ( diff --git a/src/pages/SystemFramework.tsx b/src/pages/SystemFramework.tsx index bef92f3..085f6fa 100644 --- a/src/pages/SystemFramework.tsx +++ b/src/pages/SystemFramework.tsx @@ -1,6 +1,6 @@ import React from 'react' import '@/assets/css/pages/system-framework.scss' -import system from '@/router/system' +import { getSystemRouteJson } from '@/router/system' import FitFullScreen from '@/components/common/FitFullScreen' import Sidebar from '@/components/common/sidebar' import SidebarItemList from '@/components/common/sidebar/SidebarItemList' @@ -25,7 +25,7 @@ const SystemFramework: React.FC = () => { } > - {system.map((value) => { + {getSystemRouteJson().map((value) => { return value.menu ? ( { - return jsonObject.map((value) => ({ - path: value.path, - id: value.id, - element: value.element, - Component: value.component, - handle: { - absolutePath: value.absolutePath, - name: value.name, - titlePrefix: value.titlePrefix, - title: value.title, - titlePostfix: value.titlePostfix, - icon: value.icon, - menu: value.menu, - auth: value.auth, - permission: value.permission, - autoHide: value.autoHide - }, - children: value.children && mapJsonToRoute(value.children) - })) -} - -const setTitle = (jsonObject: RouteJsonObject[], title: string): RouteJsonObject[] => { - return jsonObject.map((value) => { - if (!value.title) { - value.title = title - } - value.children && setTitle(value.children, title) - - return value - }) -} +import { getAuthRoute, mapJsonToRoute, setTitle } from '@/util/route' const root: RouteJsonObject[] = [ { @@ -80,7 +49,8 @@ const root: RouteJsonObject[] = [ component: React.lazy(() => import('@/pages/SystemFramework')), children: setTitle(system, '系统设置'), name: '系统设置', - auth: true + auth: true, + permission: true }, { path: '', @@ -98,7 +68,4 @@ const root: RouteJsonObject[] = [ } ] -const routes = mapJsonToRoute(root) - -const router = createBrowserRouter(routes) -export default router +export const getRouter = () => createBrowserRouter(mapJsonToRoute(getAuthRoute(_.cloneDeep(root)))) diff --git a/src/router/system.tsx b/src/router/system.tsx index 2f8197a..caf5d4c 100644 --- a/src/router/system.tsx +++ b/src/router/system.tsx @@ -1,4 +1,5 @@ import React from 'react' +import { getAuthRoute } from '@/util/route' const system: RouteJsonObject[] = [ { @@ -18,7 +19,6 @@ const system: RouteJsonObject[] = [ name: '用户管理', icon: React.lazy(() => import('~icons/fatweb/user.jsx')), menu: true, - permission: true, autoHide: true }, { @@ -29,7 +29,6 @@ const system: RouteJsonObject[] = [ name: '角色管理', icon: React.lazy(() => import('~icons/fatweb/role.jsx')), menu: true, - permission: true, autoHide: true }, { @@ -40,7 +39,6 @@ const system: RouteJsonObject[] = [ name: '群组管理', icon: React.lazy(() => import('~icons/fatweb/group.jsx')), menu: true, - permission: true, autoHide: true }, { @@ -51,7 +49,6 @@ const system: RouteJsonObject[] = [ name: '系统日志', icon: React.lazy(() => import('~icons/fatweb/log.jsx')), menu: true, - permission: true, autoHide: true }, { @@ -61,4 +58,6 @@ const system: RouteJsonObject[] = [ } ] +export const getSystemRouteJson = () => getAuthRoute(system, true) + export default system diff --git a/src/util/auth.tsx b/src/util/auth.tsx index b9e3d3f..082abd0 100644 --- a/src/util/auth.tsx +++ b/src/util/auth.tsx @@ -121,39 +121,6 @@ export const getUsername = async () => { return user.username } -export const getPermissionPath = (): string[] => { - const s = getLocalStorage(STORAGE_USER_INFO_KEY) - if (s === null) { - return [] - } - - const user = JSON.parse(s) as UserWithPowerInfoVo - const paths: string[] = [] - user.menus.forEach((menu) => { - paths.push(menu.url) - }) - - return paths -} - -export const hasPathPermission = (path: string) => { - return getPermissionPath().indexOf(path) !== -1 -} - -/* -export const getAuthRoute = (route: RouteJsonObject[]): RouteJsonObject[] => { - return route.map((value) => { - if (value.absolutePath) { - value.absolutePath - } - if (value.children) { - value.children = getAuthRoute(value.children) - } - return value - }) -} -*/ - export const getCaptchaSrc = () => { captcha = getCaptcha(300, 150, 4) return captcha.base64Src diff --git a/src/util/route.tsx b/src/util/route.tsx index e8a6489..3065c09 100644 --- a/src/util/route.tsx +++ b/src/util/route.tsx @@ -1,3 +1,6 @@ +import { getLocalStorage } from '@/util/browser.tsx' +import { STORAGE_USER_INFO_KEY } from '@/constants/common.constants.ts' + export const getRedirectUrl = (path: string, redirectUrl: string): string => { return `${path}?redirect=${encodeURIComponent(redirectUrl)}` } @@ -11,3 +14,72 @@ export const getFullTitle = (data: _DataNode, preTitle?: string) => { return data } + +export const getPermissionPath = (): string[] => { + const s = getLocalStorage(STORAGE_USER_INFO_KEY) + if (s === null) { + return [] + } + + const user = JSON.parse(s) as UserWithPowerInfoVo + const paths: string[] = [] + user.menus.forEach((menu) => { + paths.push(menu.url) + }) + + return paths +} + +export const hasPathPermission = (path: string) => { + return getPermissionPath().indexOf(path) !== -1 +} + +export const getAuthRoute = ( + route: RouteJsonObject[], + parentPermission: boolean = false +): RouteJsonObject[] => { + return route + .filter( + (value) => + !(value.permission || parentPermission) || hasPathPermission(value.absolutePath) + ) + .map((value) => { + if (value.children) { + value.children = getAuthRoute(value.children, parentPermission || value.permission) + } + return value + }) +} + +export const mapJsonToRoute = (jsonObject: RouteJsonObject[]): RouteObject[] => { + return jsonObject.map((value) => ({ + path: value.path, + id: value.id, + element: value.element, + Component: value.component, + handle: { + absolutePath: value.absolutePath, + name: value.name, + titlePrefix: value.titlePrefix, + title: value.title, + titlePostfix: value.titlePostfix, + icon: value.icon, + menu: value.menu, + auth: value.auth, + permission: value.permission, + autoHide: value.autoHide + }, + children: value.children && mapJsonToRoute(value.children) + })) +} + +export const setTitle = (jsonObject: RouteJsonObject[], title: string): RouteJsonObject[] => { + return jsonObject.map((value) => { + if (!value.title) { + value.title = title + } + value.children && setTitle(value.children, title) + + return value + }) +}