vue权限管理系统的实现代码
程序员文章站
2023-11-18 22:12:46
后台管理系统一般都会有权限模块,用来控制用户能访问哪些页面和哪些数据接口。大多数管理系统的页面都长这样。
左边为菜单,分为两级,右边为图表显示区域,有增删改查的按钮。...
后台管理系统一般都会有权限模块,用来控制用户能访问哪些页面和哪些数据接口。大多数管理系统的页面都长这样。
左边为菜单,分为两级,右边为图表显示区域,有增删改查的按钮。
表的结构
set names utf8mb4; set foreign_key_checks = 0; -- ---------------------------- -- table structure for t_auth_rule -- ---------------------------- drop table if exists `t_auth_rule`; create table `t_auth_rule` ( `id_pk` bigint(20) not null auto_increment, `auth_id` varchar(128) not null comment '权限id', `pauth_id` varchar(128) default null comment '父级id', `auth_name` varchar(255) not null comment '权限名称', `auth_icon` varchar(255) not null comment '权限图标', `auth_type` smallint(6) not null comment '权限类型,bit表示其属性\r\n 0x00表示可显示的菜单权限节点;\r\n 0x01表示普通节点', `auth_condition` text comment '条件', `remark` varchar(255) default null comment '备注', `is_menu` smallint(255) default '0' comment '是否为菜单,0表示非,1表示是', `weight` int(11) not null default '0' comment '权重', `rule` varchar(256) default null comment '规则路径主要对应菜单或方法的路径名称', `cr_time` timestamp not null default current_timestamp comment '创建时间', `up_time` timestamp not null default current_timestamp on update current_timestamp comment '更新时间', primary key (`id_pk`), unique key `ak_auth_id` (`auth_id`) ) engine=innodb auto_increment=264 default charset=utf8 comment='权限规则表,记录权限相关的信息,权限以父子关系存在,菜单是权限的一种。'; set foreign_key_checks = 1; set names utf8mb4; set foreign_key_checks = 0; -- ---------------------------- -- table structure for t_role_auth -- ---------------------------- drop table if exists `t_role_auth`; create table `t_role_auth` ( `id_pk` bigint(20) not null auto_increment, `role_id_fk` varchar(32) default null comment '角色id', `auth_id_fk` varchar(128) default null comment '权限id', `aa` varchar(255) default null, primary key (`id_pk`) ) engine=innodb auto_increment=77 default charset=utf8 comment='角色与权限的关系表'; set foreign_key_checks = 1;
对于菜单的权限,通过路由表匹配
addrouters(menumap) { let routerarr = []; for (let j = 0; j < routerlist.length; j++) { let obj; if (menumap['authrule::' + routerlist[j].path]) { // 找到一级菜单 obj = { path: routerlist[j].path, component: routerlist[j].component, redirect: routerlist[j].redirect, name: routerlist[j].name, meta: routerlist[j].meta, children: [] }; if (routerlist[j].children.length) { for (let k = 0; k < routerlist[j].children.length; k++) { let _fullpath = routerlist[j].children[k].path if (routerlist[j].children[k].meta) { _fullpath = routerlist[j].children[k].meta.parentpath + '/' + _fullpath } if (menumap['authrule::' + _fullpath]) { // 找到二级菜单 obj.children.push(routerlist[j].children[k]); } } } } if (obj) { routerarr.push(obj); this.$router.options.routes.push(obj); } } storage.set("routerarr", routerarr); this.$router.addroutes(routerarr); this.$router.push({ path: "/" }); },
menumap为登录时获取的权限菜单,是一个对象; routerlist为前端定义的路由表;遍历routerlist,如果routerlist的key在menumap里能找到的话,就表示该路由存在。最后生成一个过滤后的路由表,用vue提供的addroutes方法动态添加到路由中,并把过滤后的路由表存到本地。
const menumap = { '/dashboard': {path: '/dashboard', name: '首页'} } const routerlist = [ {path: '/dashboard', name: '首页', component: ..} ]
在页面刷新的时候,从本地获取路由表,添加到路由表中,代码如下,constrouterarr为基础路由表,比如登录,404等
const routerlist = storage.get('routerarr') const routerarr = constrouterarr.concat(routerlist);
对于按钮的权限
if (res.data.auth_rule_map) { let obj = {} object.keys(res.data.auth_rule_map).foreach(i => { // 将所有的按钮放到一个obj里 key 为接口地址 if (res.data.auth_rule_map[i].is_menu === 0) { // 如果是按钮 obj[res.data.auth_rule_map[i].rule] = 1 } }) storage.set("btnlist", obj); storage.set("menutree", res.data.auth_rule_map); }
auth_rule_map为接口返回权限map,把按钮的权限过滤出来存到本地。
将map添加到每个路由组件的data里,(这里有一个问题,怎么判断一个组件是否是路由组件),目前想到的是通过组件name来判断,把所有的路由组件放到一个数组里做判断。
在组件内部的按钮上加上v-if,如果this.uri__里的uri在urimap里存在就显示。
也可以通过方法来判断,如下面的__isbtnshow,不仅可以控制按钮的显示隐藏,还可以控制其样式,比如颜色等,更加灵活,推荐使用方法来控制
uri = { add_member: '/api/add_member' } export default function install (vue) { const urimap = storage.get('btnlist') //urimap['/admin/api/auth_rule/update_auth_rule.action'] = 1 vue.mixin({ created() { const arr = ['membermanage', 'paymanage', '...'] if (arr.indexof(this.$options.name) !== -1) { this.datauri__ = urimap this.uri__ = uri } }, data() { return { datauri__: {} } }, }) } <button v-if="datauri__[uri__.add_member]">添加会员</button>
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。
上一篇: vue中$nextTick的用法讲解