方法一:
首先写出前端所有页面的路由,,单独写在一个文件里或者卸载router下面的index.js文件里面都可以,这里我是单独写了一个文件,名字叫allroutes.js
allroutes.js
export default [ { path:"/goods", name:"goods", meta: {title:'goodsmanage', permission: 14 }, redirect:{path:"/goods/goodsmanage"}, children:[ { path:"goodsmanage", name:"goodsmanage", meta: {title:'goodsmanage', permission: 14 }, component: () => import("@/views/GoodsManage/GoodsManage.vue"), }, { path:"goodsupdate", name:"goodsupdate", meta: {title:'goodsupdate', permission: 14 }, component: () => import("@/views/GoodsManage/GoodsUpdate.vue"), } ]
},
{
path:"/system",
name:"system",
meta: {title:'systemmanage', permission: 14 },
children:[
{
path:"/systemmanage",
name:"systemmanage",
meta: {title:'systemmanage', permission: 14 },
component: () => import("@/views/SystemManage/menumanage.vue"),
},
{
path:"/rolemanage",
name:"rolemanage",
meta: {title:'rolemanage', permission: 14 },
component: () => import("@/views/SystemManage/rolemanage.vue"),
},{
path:"/usermanage",
name:"usermanage",
meta: {title:'usermanage', permission: 13 },
component: () => import("@/views/SystemManage/usermanage.vue"),
}
]
},
{
path:"/setting",
name:"setting",
meta: {title:'setting', permission: 14 },
component: () => import("@/views/Setting/Systemsetting.vue"),
}
]
然后在router下的index.js文件里面写好静态路由,例如
import { createRouter, createWebHistory } from 'vue-router'
import dashboard from '../views/dashboard/index.vue'
import allroutes from './allroutes'
import { filterRoutes } from "@/router/permission"
const routes = [
{
path: '/',
name: 'dashboard',
component: dashboard,
children:[]
},
{
path: '/login',
name: 'login',
// route level code-splitting
// this generates a separate chunk (about.[hash].js) for this route
// which is lazy-loaded when the route is visited.
component: function () {
return import(/* webpackChunkName: "about" */ '../views/Login/index.vue')
}
},
{
path:"/404",
component:()=>import("@/views/404/index.vue")
}
]
const router = createRouter({
history: createWebHistory(process.env.BASE_URL),
routes
})
export default router
新建permission.js文件,这里面写的是对比路由的方法
function hasAuth( permission, permissions ){
//判断是否有访问该路由的权限 , 结果是 true/false
return permissions.includes(permission);
}
/*
功能: 拿到一个路由, 用户的权限列表, 判断这个路由是否在用户的权限列表中, 返回ture/false
返回值: true 表示用户有访问该路由的权限, false表示用户没有访问该路由的权限
参数一: route 路由 , 例如: {path: '',meta:{permission:2},component: Register}
参数二: permissions 用户的权限列表 , 例如: [1, 11, 2]
*/
function hasPermission( route, permissions ){
//需要权限才能访问
if( route.meta && route.meta.permission ){
//判断是否有访问该路由的权限 , 结果是 true/false
return permissions.includes(route.meta.permission);
//不需要权限就可以访问
}else{
return true;
}
}
/*
功能: 拿到业务路由表,用户的权限列表, 根据用户的权限列表从业务路由表中过滤出用户有权限访问的路由.
参数一: routes 业务路由表 , 例如: [{path: '',meta:{permission:2},component: Register},...]
参数二: permissions 用户的权限列表 , 例如: [1, 11, 2]
*/
export function filterRoutes( routes, permissions ){
var accessRoutes = [];
//过滤routes这个路由表
accessRoutes = routes.filter((route)=>{
//判断: 如果route表示的路由规则在用户的权限列表中,则用户有权限访问该路由,该路由就需要过滤出来.
if( hasPermission( route, permissions ) ){
//如果route 这个路由有子路由表, 则继续过滤子路由表
if( route.children && route.children.length ){
//继续过滤子路由表( 调用 filterRoutes 自身 过滤子路由表 )
route.children = filterRoutes( route.children, permissions )
}
console.log(accessRoutes)
return true;
}else{
return false;
}
})
//返回最终过滤出来的 用户有权限访问的路由.
return accessRoutes;
}
在登陆的时候根据权限的不同动态的添加 login.vue
<template>
<h1>This is Goods</h1>
<h1 @click="go">tiaozhuan </h1>
</template>
<script>
import routes from "../../router/allroutes"
import { filterRoutes } from "@/router/permission"
// import router from '@/router'
import { useRouter } from 'vue-router'
export default {
name:"login",
setup(m,n,z){
const router = useRouter()
console.log(m)
console.log(n)
console.log(z)
var accessRoutes = filterRoutes( routes , "14" )
console.log(accessRoutes)
accessRoutes.forEach((route)=>{
router.options.routes.push(route) //循环一次, 添加一条路由
})
const go = function(){
router.push("/goods")
}
return {
go
}
}
}
</script>
方法二:
根据路由里面的meta属性搭配路由守卫进行判断
如果一个网站有不同的角色,比如 管理员 和 普通用户 ,要求不同的角色能访问的页面是不一样的
这个时候我们就可以 把所有的页面都放在路由表里 ,只要 在访问的时候判断一下角色权限 。如果有权限就让访问,没有权限的话就拒绝访问,跳转到404页面
vue-router 在构建路由时提供了元信息 meta 配置接口,我们可以在元信息中添加路由对应的权限,然后在路由守卫中检查相关权限,控制其路由跳转。
可以在每一个路由的 meta 属性里,将能访问该路由的角色添加到 roles 里。用户每次登陆后,将用户的角色返回。然后在访问页面时,把路由的 meta 属性和用户的角色进行对比,如果用户的角色在路由的 roles 里,那就是能访问,如果不在就拒绝访问。
import VueRouter from 'vue-router';
Vue.use(VueRouter)
...
routes: [
{
path: '/login',
name: 'login',
meta: {
roles: ['admin', 'user']
},
component: () => import('../components/Login.vue')
},
{
path: 'home',
name: 'home',
meta: {
roles: ['admin']
},
component: () => import('../views/Home.vue')
},
]
const router = new VueRouter({
routes
})
export default router
在app.vue文件下引入,注册全局的路由守卫
app.vue
//假设有两种角色:admin 和 user
//从后台获取的用户角色
const role = 'user'
//当进入一个页面是会触发导航守卫 router.beforeEach 事件
router.beforeEach((to,from,next)=>{
if(to.meta.roles.includes(role)){
next() //放行
}esle{
next({path:"/404"}) //跳到404页面
}
})
自此基本上路由的权限控制就完成了
题外话 在路由守卫中也能很好的解决匹配不到路由转404页面的业务需求,实现如下:
import router from ‘./router‘
router.beforeEach((to, from, next) => {
// ...
if (to.matched.length === 0) {
next('/404')
} else {
next()
}
//console.log(to, from, next, '路由守卫')
})