应用场景:在后台一些项目中分为很多权限,例如超级管理员和普通管理员,后台展现的内容需要根据权限来判断是否显示操作员对应的内容,这时候需要设置全局自定义指令v-permission来进行权限控制。
//index.vue
<template>
<IndexChart v-permission="['getStatistics3,GET']"></IndexChart> //显示,后端给的权限数据包含有这个参数
<IndexChart v-permission="['getStatistics33333,GET']"></IndexChart> //不显示,后端给的权限数据找不到这个参数
</template>
//permission.js
import store from '~/store'
function hasPermission(value, el=false){
//如果自定义指令设置的不是数组,则抛出异常
if(!Array.isArray(value)){
throw new Error(`需要配置权限,例如 v-permission="['getStatistics3,GET']" `)
}
//根据传过来的value,在state中的ruleNames中是否包含有这个value
const hasAuth = value.findIndex(e=>store.state.ruleNames.includes(e))!=-1
//如果找不到对应的数据,则移除这个el节点
if(el && !hasAuth){
el.parentNode && el.parentNode.removeChild(el)
}
return hasAuth
}
export default {
//如果app.use()中的插件是一个对象,必须提供 install 方法。如果插件是一个函数,它会被作为 install 方法。
//install 方法调用时,会将 app 作为参数传入,此时就可以在别的文件中使用app.directive()了
install(app){
app.directive("permission",{
//指令的钩子会传递2个参数
//el:指令绑定到的元素,这可以用于直接操作 DOM
//binding.value:传递给指令的值,例如在 v-permission="['getStatistics3,GET']" 中,值是 ['getStatistics3,GET']
mounted(el,binding) {
hasPermission(binding.value,el)
},
})
}
}
//main.js
import { createApp } from 'vue'
import App from './App.vue'
const app = createApp(App)
import permission from '~/directives/permission' //引入permission.js
app.use(permission)
app.mount('#app')
//store中的index.js
import { createStore } from 'vuex'
const store = createStore({
state() {
return {
//用户权限
ruleNames: []
}
},
mutations: {
//获取用户权限
GET_RULENAMES(state, ruleNames) {
state.ruleNames = ruleNames
}
},
actions: {
getinfon({ commit }) {
return new Promise((resolve, reject) => {
getinfo().then(res => {
commit('GET_RULENAMES', res.ruleNames)
resolve(res)
}).catch(err => reject(err))
})
},
}
})
export default store