个人中心 Profile.vue
商店 Shop.vue
购物车 Cart.vue
└── 购物车列表 CartList.vue
├── 商品 Product.vue
└── 彩票 Lottery.vue
[
{pid:-1,path:'/cart',name:'购物车',id:1,auth:'cart'},
{pid:1,path:'/cart/cart-list',name:'购物车列表',id:4,auth:'cart-list'},
{pid:4,path:'/cart/cart-list/lottery',auth:'lottery',id:5,name:'彩票'},
{pid:4,path:'/cart/cart-list/product',auth:'product',id:6,name:'商品'},
{pid:-1,path:'/shop',name:'商店',id:2,auth:'shop'},
{pid:-1,path:'/profile',name:'个人中心',id:3,auth:'store'},
];
let express = require('express');
let app = express();
app.all('*', function (req, res, next) {
res.header('Access-Control-Allow-Origin', '*');
//Access-Control-Allow-Headers ,可根据浏览器的F12查看,把对应的粘贴在这里就行
res.header('Access-Control-Allow-Headers', 'Content-Type');
res.header('Access-Control-Allow-Methods', '*');
res.header('Content-Type', 'application/json;charset=utf-8');
next();
});
app.get('/roleAuth',(req,res)=>{
res.json({
menuList:[
{pid:-1,path:'/cart',name:'购物车',id:1,auth:'cart'},
{pid:1,path:'/cart/cart-list',name:'购物车列表',id:4,auth:'cart-list'},
{pid:4,path:'/cart/cart-list/lottery',auth:'lottery',id:5,name:'彩票'},
{pid:4,path:'/cart/cart-list/product',auth:'product',id:6,name:'商品'},
{pid:-1,path:'/shop',name:'商店',id:2,auth:'shop'},
{pid:-1,path:'/profile',name:'个人中心',id:3,auth:'profile'},
]
})
})
app.listen(3000);
let getMenuList = (list) => {
let auths = [];
function getList(pid){
return list.filter(l=>{
if(l.pid === pid){
auths.push(l.auth); // 提取用户权限
let children = getList(l.id);
l.children = children.length>0?children:null;
return l;
}
});
}
let menuList = getList(-1); // 通过根循环列表
return {menuList,auths};
}
// 获取菜单列表
export default new Vuex.Store({
state: {
menuList:[], // 菜单列表
authList:[], // 权限列表
hasAuthMenu: false // 默认没有权限菜单,如果获取菜单后改为true
},
mutations: {
setMenuList(state,menuList){
state.menuList = menuList;
},
authList(state,auths){
state.authList = auths;
},
hasAuthMenu(state){
state.hasAuthMenu = true;
}
},
actions: {
async getMenuList({commit}){
let {data} = await axios.get('http://localhost:3000/roleAuth');
let {menuList,auths} = getMenuList(data.menuList);
commit('setMenuList',menuList);
commit('authList',auths);
commit('hasAuthMenu');
return auths;
}
}
});
<el-menu default-active="2" class="el-menu-vertical-demo">
<el-submenu index="1">
<template slot="title">导航一</template>
<el-submenu index="1-1">
<template slot="title">选项1-1</template>
<el-menu-item index="1-1-1">选项1-1-1</el-menu-item>
<el-menu-item index="1-1-2">选项1-1-2</el-menu-item>
</el-submenu>
<el-menu-item index="1-2">选项1-2</el-menu-item>
</el-submenu>
<el-menu-item index="2">
导航二
</el-menu-item>
<el-menu-item index="3">
导航三
</el-menu-item>
<el-menu-item index="4">
导航四
</el-menu-item>
</el-menu>
Home.vue
<template>
<div class="home">
<el-menu default-active="2" class="el-menu-vertical-demo" :router="true">
<template v-for="m in menuList">
<el-menu-item :index="m.path" :key="m.auth" v-if="!m.children">
{{m.name}}
</el-menu-item>
<ReSub :m="m" :key="m.auth" v-else></ReSub>
</template>
</el-menu>
</div>
</template>
ReSub.vue
<template>
<el-submenu :index="m.auth">
<template slot="title">
<router-link :to="m.path">{{m.name}}</router-link>
</template>
<template v-for="l in m.children">
<el-menu-item v-if="!l.children" :index="l.path" :key="l.auth">{{l.name}}</el-menu-item>
<ReSub v-else :key="l.auth" :m="l"></ReSub>
</template>
</el-submenu>
</template>
<script>
export default {
name:'ReSub',
props:['m']
}
</script>
// 权限路由
export let authRoutes = [
{
path:'/cart',
name:'cart',
component:()=>import('@/views/menu/Cart'),
children:[
{
path:'cart-list',
name:'cart-list',
component:()=>import('@/views/menu/CartList'),
children:[
{
path:'lottery',
name:'lottery',
component:()=>import('@/views/menu/Lottery'),
},
{
path:'product',
name:'product',
component:()=>import('@/views/menu/Product'),
}
]
}
]
},
{
path:'/profile',
name:'profile',
component:()=>import('@/views/menu/Profile'),
},
{
path:'/shop',
name:'shop',
component:()=>import('@/views/menu/Shop'),
}
]
// 默认路由
let defaultRoutes = [
{
path: '/',
name: 'home',
component: Home
},
{
path: '*',
component: NotFound
}
]
router.beforeEach(async (to,from,next)=>{
if(!store.state.hasAuthMenu){
// 1) 获取菜单列表
let auths = await store.dispatch('getMenuList');
// 2) 获取筛选后的路由
let newRoutes = await store.dispatch('authRoutes',auths);
// 3) 根据权限添加路由
router.addRoutes(newRoutes);
next({...to,replace:true});
}else{
next();
}
});
// 获取路由数据
let getRoutes = (auths)=>{
function r(authRoutes){
return authRoutes.filter(route=>{
// 有权限
if(auths.includes(route.name)){
if(route.children){ // 有孩子 递归孩子
route.children = r(route.children);
}
return route;
}
})
}
return r(authRoutes);
}
// vuex中获取晒出的路由
async authRoutes({commit},auths){
// 全部路由 + 权限 => 晒出需要的路由
return getRoutes(auths)
},