路由权限
router.js
import Vue from "vue"; import VueRouter from "vue-router"; import NotFound from "../views/Notfound/404.vue"; import Forbidden from "../views/User/403.vue"; import NProgress from "nprogress"; import findLast from "loadsh/findLast"; import { notification } from "ant-design-vue"; import { check, isLogin } from "../utils/auth"; import "nprogress/nprogress.css"; Vue.use(VueRouter); const routes = [ // User { path: "/user", hideInMenu: true, component: () => import(/* webpackChunkName: "user" */ "../layouts/Userlayout.vue"), redirect: "/user/login", children: [ { path: "/user/login", name: "login", component: () => import(/* webpackChunkName: "user" */ "../views/User/login") }, { path: "user/register", name: "register", component: () => { import(/* webpackChunkName: "user" */ "../views/User/register"); } } ] }, // dashboard { path: "/", meta: { authority: ["user", "admin"] }, component: () => import(/* webpackChunkName: "layout" */ "../layouts/BasicLayout.vue"), children: [ { path: "/dashboard", component: { render: h => h("router-view") }, name: "dashboard", meta: { icon: "dashboard", title: "仪表盘" }, children: [ { path: "/dashboard/analysis", name: "analysis", meta: { title: "分析页" }, component: () => import( /* webpackChunkName: "dashaboard" */ "../views/Dashaboard/analysis.vue" ) } ] } ] }, // form { path: "/form", name: "form", component: () => import(/* webpackChunkName: "layout" */ "../layouts/BasicLayout.vue"), redirect: "/form/basic-form", meta: { icon: "form", title: "表单", authority: ["admin"] }, children: [ { path: "/form/basic-form", name: "basicform", meta: { title: "基础表单" }, component: () => import(/*webpackChunkName: "form" */ "../views/Forms/BasicForm") }, { path: "/form/step-form", name: "stepform", hideChildrenInMenu: true, meta: { title: "分步表单" }, component: () => import( /*webpackChunkName: "form" */ "../views/Forms/StepForm/StepForm.vue" ), redirect: "/form/step-from/info", children: [ { path: "/form/step-from/info", name: "info", component: () => import( /*webpackChunkName: "from"*/ "../views/Forms/StepForm/Info.vue" ) }, { path: "/form/step-from/comfirm", name: "comfirm", component: () => import( /*webpackChunkName: "from"*/ "../views/Forms/StepForm/Comfirm.vue" ) }, { path: "/form/step-from/result", name: "result", component: () => import( /*webpackChunkName: "from"*/ "../views/Forms/StepForm/Result.vue" ) } ] } ] },// 404 { path: "*", name: "404", hideInMenu: true, component: NotFound }, //403 { path: "/403", name: "403", hideInMenu: true, component: Forbidden } ]; const router = new VueRouter({ mode: "history", base: process.env.BASE_URL, routes }); router.beforeEach((to, from, next) => { if (to.path !== from.path) { NProgress.start(); } const record = findLast(to.matched, record => record.meta.authority); if (record && !check(record.meta.authority)) { if (!isLogin() && to.path !== "/user/login") { next({ path: "/user/login" }); } else if (to.path !== "/403") { notification.error({ message: "403", description: "您没有权限访问该页面,请联系管理员咨询" }); next({ path: "/403" }); } NProgress.done(); } next(); }); router.afterEach(() => { NProgress.done(); }); export default router;
siderMenu.vue
<template> <div style="width: 256px"> <a-menu :selectedKeys="selectedKeys" :openKeys.sync="openKeys" mode="inline" :theme="theme" > <template v-for="item in menuData"> <a-menu-item v-if="!item.children" :key="item.path" @click="$router.push({ path: item.key, query: $route.query })" > <a-icon v-if="item.meta.icon" :type="item.meta.icon" /> <span>{{ item.meta.title }}</span> </a-menu-item> <sub-menu v-else :menu-info="item" :key="item.path" /> </template> </a-menu> </div> </template> <script> import SubMenu from "./SubMenu"; import { check } from "../utils/auth"; export default { components: { "sub-menu": SubMenu }, props: { theme: { type: String, default: "dark" } }, watch: { "$route.path": function(val) { this.selectedKeys = this.selectedKeysMap[val]; this.openKeys = this.collapsed ? [] : this.openKeysMap[val]; } }, data() { this.selectedKeysMap = {}; this.openKeysMap = {}; const menuData = this.getMenuData(this.$router.options.routes); return { collapsed: false, menuData, selectedKeys: this.selectedKeysMap[this.$route.path], openKeys: this.collapsed ? [] : this.openKeysMap[this.$route.path] }; }, methods: { toggleCollapsed() { this.collapsed = !this.collapsed; }, getMenuData(routes = [], parentKeys = [], selectedKey) { const menuData = []; for (let item of routes) { if (item.meta && item.meta.authority && !check(item.meta.authority)) { continue; } if (item.name && !item.hideInMenu) { this.openKeysMap[item.path] = parentKeys; this.selectedKeysMap[item.path] = [selectedKey || item.path]; const newItem = { ...item }; delete newItem.children; if (item.children && !item.hideChildrenInMenu) { newItem.children = this.getMenuData(item.children, [ ...parentKeys, item.path ]); } else { this.getMenuData( item.children, selectedKey ? parentKeys : [...parentKeys, item.path], selectedKey || item.path ); } menuData.push(newItem); } else if ( !item.hideInMenu && !item.hideChildrenInMenu && item.children ) { menuData.push( ...this.getMenuData(item.children, [...parentKeys, item.path]) ); } } return menuData; } } }; </script>
subMenu.vue
<template functional> <a-sub-menu :key="props.menuInfo.path"> <span slot="title"> <a-icon v-if="props.menuInfo.meta.icon" :type="props.menuInfo.meta.icon" /> <span>{{ props.menuInfo.meta.title }}</span> </span> <template v-for="item in props.menuInfo.children"> <a-menu-item v-if="!item.children" :key="item.path" @click=" parent.$router.push({ path: item.path, query: parent.$route.query }) " > <a-icon v-if="item.meta.icon" :type="item.meta.icon"></a-icon> <span>{{ item.meta.title }}</span> </a-menu-item> <sub-menu v-else :key="item.path" :menu-info="item" /> </template> </a-sub-menu> </template> <script> export default { props: ["menuInfo"] }; </script>
auth.js
export function getCurrentAuthority() { return ["admin"]; } export function check(authority) { const current = getCurrentAuthority(); return current.some(item => authority.includes(item)); } export function isLogin() { const current = getCurrentAuthority(); return current && current[0] !== "guest"; }