共计 2923 个字符,预计需要花费 8 分钟才能阅读完成。
如何在 vue 我的项目中通过后端的权限数据对组件中的按钮、元素进行显示暗藏?(如管理员能看到所有按钮 非管理员只能应用某些按钮),咱们在登入时通过接口取得如下用户的菜单数据,包含每个菜单中有 opFlag:1
代表以后此节点为菜单,否则 opFlag:2
代表以后用户的这个菜单下能够显示(有权限应用)的按钮:
菜单树数据(含按钮):
{
"id": 932,
"opName": "业务管理",
"opFlag": 1,
"url": "/BusinessManagement",
"icon": "#iconscx",
"btnList": "","children": [ {"id": 1041,"opName":" 客户治理 ","opFlag": 1,"url":"/CustomerManagement","icon":"",
"children": [{
"id": 1160,
"opName": "删除",
"opFlag": 2,
"url": "del",
"icon": "","children": []},{
"id": 1161,
"opName": "编辑",
"opFlag": 2,
"url": "edit",
"icon": "","children": []}]
}, {
"id": 933,
"opFlag": 1,
"url": "/userManagement",
"icon": "","children": [{"id": 934,"opName":" 用户列表 ","opFlag": 1,"url":"",
"icon": "","children": [{"id": 937,"opName":" 申请账号 ","opFlag": 1,"url":"/userManagement/apply","icon":"",
"children": []}, ]
}, ]
}]
}
这里咱们不须要关注 opFlag:1
的菜单数据,只关注 opFlag:2
的按钮数据。
通过以上现有的按钮数据,在 vuex 中定义键值形式的权限表。通过 mutations
把对应菜单的按钮权限数组项一一 push
到 vuex 中:
store.js
state: {"/userManagement": [], // 用户模块权限
"/CustomerManagement": [] // 客户模块},
mutations: {setAuthList(state, auth) {state[auth.name].push(auth.authList);
},
}
state 中对应的键值 "url":["权限 1","权限 2"]
接下来须要拆散出按钮数据,operations
为菜单树数据:
if(operations && operations.length > 0 && operations[0].children) {_this.menuData = this.filterMenuData(operations[0].children);
}else {_this.menuData = [];
}
setBtnListStore(url,auth){
// 以按钮所属父级模块的 url 为模块名设置到 vuex 中,要在 vuex 中当时定义对应模块
if(this.$store.state[url]){this.$store.commit('setAuthList',{name:url,authList:auth});
}
},
filterMenuData(data){ // 过滤出不含按钮的菜单数据
let _that = this;
let menuData = (function deepCopy( source,pUrl) {let target = []
for (var k in source) {if (source.hasOwnProperty(k)) {if ( typeof source[ k] === 'object') {if( Array.isArray(source)){ // 以后在 cildren 当中 递归深拷贝 json
if(source[ k].opFlag == 1){ // 菜单,如果是菜单才进行下一步的深拷贝
target[k] = deepCopy(source[ k] ,source.url)
}else{// 按钮
if(pUrl){_that.setBtnListStore(pUrl,source[k].url); // 设置到 vuex 中
}
}
}else{target[ k] = deepCopy(source[ k],source.url )
}
} else {target[ k] = source[k]
}
}
}
return target
})(data)
return menuData;
},
咱们获取了树形的菜单数据后对菜单进行渲染同时通过 filterMenuData
过滤到 opFlag:2
的数据,而后通过 setBtnListStore
把菜单和对应的按钮列表存储入 vuex 中。
对 operations
菜单数据操作前先深拷贝一次,免得影响原有数据,在拷贝递归的同时获取按钮权限信息。
接下来就是撸一个 vue 自定义指令
,创立authVueDirective.js
用于在 vue 中创立自定义指令 auth:
import Vue from 'vue';
let authList = []
let setAuthList = (list)=>{
// 在组件中传入以后用户的权限列表
authList = list||[];}
const hasPermission = userPermission => {
// 以后用户的权限列表
return authList.some(i => userPermission.includes(i));
};
// 权限指令
Vue.directive("auth", {inserted: (el, binding, vnode) => {if (!hasPermission(binding.value)) {el.parentNode.removeChild(el);
}
}
});
export default {setAuthList}
authList
是一个用于存储权限的列表,在 v-auth="['xxx']"
应用时,判断 v-auth
所需的权限是否存在于 authList
列表中,否则不存在示意以后无权限则移除元素(按钮),到这里咱们就实现了整个按钮权限的所需工作,接下来看看如何在组件中应用它:
在 /CustomerManagement
页面中引入 authVueDirective.js
存储以后页面的权限列表(伪代码):
template:<el-button @click="del"
v-auth="['del']"> 删除 </el-button>
<el-button @click="add"
v-auth="['add']"> 增加 </el-button>
import vauth from '@/assets/js/authVueDirective.js';
created(){
// 设置按钮权限
vauth.setAuthList(this.$store.state['/CustomerManagement']);
// 这里的 setAuthList 相当于 vauth.setAuthList(['del','edit']);
},
最终删除按钮在因为咱们有 del
能显示进去,增加按钮则不能显示。