123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265 |
- import { defineStore } from 'pinia';
- import router, { constantRoutes, dynamicRoutes } from '@/router';
- import store from '@/store';
- import { getRouters } from '@/api/menu';
- import auth from '@/plugins/auth';
- import { RouteRecordRaw } from 'vue-router';
- import Layout from '@/layout/index.vue';
- import ParentView from '@/components/ParentView/index.vue';
- import InnerLink from '@/layout/components/InnerLink/index.vue';
- import { createCustomNameComponent } from '@/utils/createCustomNameComponent';
- // 匹配views里面所有的.vue文件
- const modules = import.meta.glob('./../../views/**/*.vue');
- export const usePermissionStore = defineStore('permission', () => {
- const routes = ref<RouteRecordRaw[]>([]);
- const addRoutes = ref<RouteRecordRaw[]>([]);
- const defaultRoutes = ref<RouteRecordRaw[]>([]);
- const topbarRouters = ref<RouteRecordRaw[]>([]);
- const sidebarRouters = ref<RouteRecordRaw[]>([]);
- // 菜单
- // type 1 系统内地址 2 外链
- const menuState = reactive({
- leftMenu: [
- { label: '全域地图', path: '/globalMap', path2: '/globalMap2', type: '1', checked: false },
- { label: '一图作战', path: '/', path2: '/index2', type: '1', checked: false },
- { label: '总体态势', path: 'http://19.155.220.218/#/considerable-web/overallSituation?type=full', path2: 'http://19.155.220.218/#/considerable-web/overallSituation?type=large', type: '2', checked: false },
- { label: '非煤矿山', path: 'http://19.155.220.218/#/considerable-web/noCoalMine?type=full', path2: 'http://19.155.220.218/#/considerable-web/noCoalMine?type=large', type: '2', checked: false },
- { label: '粉尘防爆', path: 'http://19.155.220.218/#/considerable-web/dustIgnitionPproof?type=full', path2: 'http://19.155.220.218/#/considerable-web/dustIgnitionPproof?type=large', type: '2', checked: false }
- ],
- rightMenu: [
- { label: '地质灾害', path: 'http://19.155.220.218/#/considerable-web/geologicalDisaster?type=full', path2: 'http://19.155.220.218/#/considerable-web/geologicalDisaster?type=large', type: '2', checked: false },
- { label: '森林防火', path: 'http://19.155.220.218/#/considerable-web/forestFireproof?type=full', path2: 'http://19.155.220.218/#/considerable-web/forestFireproof?type=large', type: '2', checked: false },
- { label: '三防', path: 'http://19.155.220.218/#/considerable-web/threeProofings?type=full', path2: 'http://19.155.220.218/#/considerable-web/threeProofings?type=large', type: '2', checked: false },
- { label: '危化品', path: 'http://19.155.220.218/#/considerable-web/hazardousChemicals?type=full', path2: 'http://19.155.220.218/#/considerable-web/hazardousChemicals?type=large', type: '2', checked: false }
- ]
- });
- const activeMenu = ref('left');
- const menuIndex = ref(1);
- const setMenu = (route) => {
- let direction = '';
- let index = -1;
- for (let i = 0; i < menuState.leftMenu.length; i++) {
- if (menuState.leftMenu[i].path === route.path || menuState.leftMenu[i].path2 === route.path) {
- index = i;
- direction = 'left';
- break;
- }
- }
- if (index === -1) {
- for (let k = 0; k < menuState.rightMenu.length; k++) {
- if (menuState.rightMenu[k].path === route.path) {
- index = k;
- direction = 'right';
- break;
- }
- }
- }
- if (index !== -1) {
- activeMenu.value = direction;
- menuIndex.value = index;
- }
- };
- const getRoutes = (): RouteRecordRaw[] => {
- return routes.value;
- };
- const getSidebarRoutes = (): RouteRecordRaw[] => {
- return sidebarRouters.value;
- };
- const getTopbarRoutes = (): RouteRecordRaw[] => {
- return topbarRouters.value;
- };
- const setRoutes = (newRoutes: RouteRecordRaw[]): void => {
- addRoutes.value = newRoutes;
- routes.value = constantRoutes.concat(newRoutes);
- };
- const setDefaultRoutes = (routes: RouteRecordRaw[]): void => {
- defaultRoutes.value = constantRoutes.concat(routes);
- };
- const setTopbarRoutes = (routes: RouteRecordRaw[]): void => {
- topbarRouters.value = routes;
- };
- const setSidebarRouters = (routes: RouteRecordRaw[]): void => {
- sidebarRouters.value = routes;
- };
- const generateRoutes = async (): Promise<RouteRecordRaw[]> => {
- const res = await getRouters();
- const { data } = res;
- const sdata = JSON.parse(JSON.stringify(data));
- const rdata = JSON.parse(JSON.stringify(data));
- const defaultData = JSON.parse(JSON.stringify(data));
- const sidebarRoutes = filterAsyncRouter(sdata);
- const rewriteRoutes = filterAsyncRouter(rdata, undefined, true);
- const defaultRoutes = filterAsyncRouter(defaultData);
- const asyncRoutes = filterDynamicRoutes(dynamicRoutes);
- asyncRoutes.forEach((route) => {
- router.addRoute(route);
- });
- setRoutes(rewriteRoutes);
- setSidebarRouters(constantRoutes.concat(sidebarRoutes));
- setDefaultRoutes(sidebarRoutes);
- setTopbarRoutes(defaultRoutes);
- // 路由name重复检查
- duplicateRouteChecker(asyncRoutes, sidebarRoutes);
- return new Promise<RouteRecordRaw[]>((resolve) => resolve(rewriteRoutes));
- };
- /**
- * 遍历后台传来的路由字符串,转换为组件对象
- * @param asyncRouterMap 后台传来的路由字符串
- * @param lastRouter 上一级路由
- * @param type 是否是重写路由
- */
- const filterAsyncRouter = (asyncRouterMap: RouteRecordRaw[], lastRouter?: RouteRecordRaw, type = false): RouteRecordRaw[] => {
- return asyncRouterMap.filter((route) => {
- if (type && route.children) {
- route.children = filterChildren(route.children, undefined);
- }
- // Layout ParentView 组件特殊处理
- if (route.component?.toString() === 'Layout') {
- route.component = Layout;
- } else if (route.component?.toString() === 'ParentView') {
- route.component = ParentView;
- } else if (route.component?.toString() === 'InnerLink') {
- route.component = InnerLink;
- } else {
- route.component = loadView(route.component, route.name as string);
- }
- if (route.children != null && route.children && route.children.length) {
- route.children = filterAsyncRouter(route.children, route, type);
- } else {
- delete route.children;
- delete route.redirect;
- }
- return true;
- });
- };
- const filterChildren = (childrenMap: RouteRecordRaw[], lastRouter?: RouteRecordRaw): RouteRecordRaw[] => {
- let children: RouteRecordRaw[] = [];
- childrenMap.forEach((el) => {
- if (el.children && el.children.length) {
- if (el.component?.toString() === 'ParentView' && !lastRouter) {
- el.children.forEach((c) => {
- c.path = el.path + '/' + c.path;
- if (c.children && c.children.length) {
- children = children.concat(filterChildren(c.children, c));
- return;
- }
- children.push(c);
- });
- return;
- }
- }
- if (lastRouter) {
- el.path = lastRouter.path + '/' + el.path;
- if (el.children && el.children.length) {
- children = children.concat(filterChildren(el.children, el));
- return;
- }
- }
- children = children.concat(el);
- });
- return children;
- };
- return {
- routes,
- topbarRouters,
- sidebarRouters,
- defaultRoutes,
- menuState,
- activeMenu,
- menuIndex,
- setMenu,
- getRoutes,
- getSidebarRoutes,
- getTopbarRoutes,
- setRoutes,
- generateRoutes,
- setSidebarRouters
- };
- });
- // 动态路由遍历,验证是否具备权限
- export const filterDynamicRoutes = (routes: RouteRecordRaw[]) => {
- const res: RouteRecordRaw[] = [];
- routes.forEach((route) => {
- if (route.permissions) {
- if (auth.hasPermiOr(route.permissions)) {
- res.push(route);
- }
- } else if (route.roles) {
- if (auth.hasRoleOr(route.roles)) {
- res.push(route);
- }
- }
- });
- return res;
- };
- export const loadView = (view: any, name: string) => {
- let res;
- for (const path in modules) {
- const dir = path.split('views/')[1].split('.vue')[0];
- if (dir === view) {
- res = createCustomNameComponent(modules[path], { name });
- }
- }
- return res;
- };
- // 非setup
- export const usePermissionStoreHook = () => {
- return usePermissionStore(store);
- };
- interface Route {
- name?: string | symbol;
- path: string;
- children?: Route[];
- }
- /**
- * 检查路由name是否重复
- * @param localRoutes 本地路由
- * @param routes 动态路由
- */
- function duplicateRouteChecker(localRoutes: Route[], routes: Route[]) {
- // 展平
- function flatRoutes(routes: Route[]) {
- const res: Route[] = [];
- routes.forEach((route) => {
- if (route.children) {
- res.push(...flatRoutes(route.children));
- } else {
- res.push(route);
- }
- });
- return res;
- }
- const allRoutes = flatRoutes([...localRoutes, ...routes]);
- const nameList: string[] = [];
- allRoutes.forEach((route) => {
- const name = route.name.toString();
- if (name && nameList.includes(name)) {
- const message = `路由名称: [${name}] 重复, 会造成 404`;
- console.error(message);
- ElNotification({
- title: '路由名称重复',
- message,
- type: 'error'
- });
- return;
- }
- nameList.push(route.name.toString());
- });
- }
- export default usePermissionStore;
|