1. 定义 v-permission 指令
创建一个文件来定义自定义指令,例如 directives/permission.js。
| |
| |
| import { useUserStore } from '../store/userStore'; |
| |
| export default { |
| mounted(el, binding) { |
| const { value: permissionName } = binding; |
| |
| |
| const userStore = useUserStore(); |
| const permissions = userStore.permissions; |
| |
| if (!permissions.includes(permissionName)) { |
| el.style.display = 'none'; |
| } |
| }, |
| updated(el, binding) { |
| const { value: permissionName } = binding; |
| |
| const userStore = useUserStore(); |
| const permissions = userStore.permissions; |
| |
| if (!permissions.includes(permissionName)) { |
| el.style.display = 'none'; |
| } else { |
| el.style.display = ''; |
| } |
| } |
| }; |
2. 在主文件中全局注册指令
在主入口文件中(如 main.js),全局注册自定义指令。
| |
| import { createApp } from 'vue'; |
| import App from './App.vue'; |
| import router from './router'; |
| import { createPinia } from 'pinia'; |
| import permission from './directives/permission'; |
| |
| const app = createApp(App); |
| |
| const pinia = createPinia(); |
| app.use(pinia); |
| app.use(router); |
| |
| |
| app.directive('permission', permission); |
| |
| app.mount('#app'); |
3. 使用指令来控制按钮显示
在需要控制按钮显示的地方,使用 v-permission 指令,并传递按钮的 name 作为指令的值。
| <template> |
| <div> |
| <button v-permission="'edit'" name="edit-button">Edit</button> |
| <button v-permission="'delete'" name="delete-button">Delete</button> |
| <button v-permission="'view'" name="view-button">View</button> |
| </div> |
| </template> |
4. 设置用户权限存储 (假设你使用的是 Pinia)
| |
| import { defineStore } from 'pinia'; |
| |
| export const useUserStore = defineStore('user', { |
| state: () => ({ |
| permissions: ['view', 'edit'], |
| }), |
| actions: { |
| setPermissions(permissions) { |
| this.permissions = permissions; |
| }, |
| }, |
| }); |
5. 其它
如果使用 el.style.display = 'none' 来隐藏按钮,用户可以在浏览器的开发者工具(控制台)中手动修改 display 样式来显示按钮。这种方式并不是真正的安全控制,只是简单地在前端隐藏元素。
| if (!permissions.includes(permissionName)) { |
| el.parentNode && el.parentNode.removeChild(el); |
| } |
也可以使用v-if
| <template> |
| <div> |
| |
| <button v-if="hasPermission('edit')" name="edit-button">Edit</button> |
| <button v-if="hasPermission('delete')" name="delete-button">Delete</button> |
| </div> |
| </template> |
| |
| <script setup> |
| import { computed } from 'vue'; |
| import { useUserStore } from '../store/userStore'; |
| |
| const userStore = useUserStore(); |
| |
| |
| const hasPermission = (permissionName) => { |
| return computed(() => userStore.permissions.includes(permissionName)); |
| }; |
| </script> |
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 单元测试从入门到精通
· 上周热点回顾(3.3-3.9)
· Vue3状态管理终极指南:Pinia保姆级教程