🔐 v-auth 权限控制指令
🎯 功能简介
v-auth 指令用于基于用户权限控制 UI 元素的显示与隐藏,是构建权限管理系统的核心组件之一。当用户没有特定权限时,带有该指令的元素将被自动从 DOM 中移除。
🚀 使用方法
基本用法
vue
<!-- 单个权限控制 -->
<button v-auth="'user-add'">添加用户</button>
<!-- 多权限控制(需同时满足所有权限) -->
<button v-auth="['user-edit', 'user-delete']">高级操作</button>⚠️ 注意事项
- 指令只在元素挂载时执行一次,不会响应权限数据的动态变化
- 元素一旦被移除就不会自动恢复,即使后续获得了相应权限
- 权限值通常使用
模块-操作的格式,例如:user-add、report-export等
📝 完整示例
下面是一个交互式的权限控制演示组件:
vue
<template>
<div>
<h2>权限指令演示</h2>
<section class="auth-control">
<h3>权限控制</h3>
<div>
<label>当前路由: {{ authStore.routeName }}</label>
<div class="permission-panel">
<h4>为当前页面添加权限:</h4>
<div>
<input v-model="newPermission" placeholder="输入新权限" />
<button @click="addPermission">添加</button>
</div>
<div>
<p class="lh-32px">1. 指令只在元素挂载时执行,暂时不会响应权限数据的变化,<br>
2. 元素一旦被移除就永久消失,即使后来有了权限也不会自动恢复,后续确实有这样的场景我可以改造指令,<br>
暂时没有动态变化的场景</p>
</div>
<div class="permission-list">
<span v-for="perm in currentPermissions" :key="perm" class="permission-tag">
{{ perm }}
<button @click="removePermission(perm)">×</button>
</span>
</div>
</div>
</div>
</section>
<section class="auth-test">
<h3>指令测试</h3>
<!-- 需要 add 权限 -->
<div>
<button v-auth="'auth-add'" class="auth-btn">添加按钮 (需要 "add" 权限)</button>
</div>
<!-- 需要 edit 权限 -->
<div>
<button v-auth="'auth-edit'" class="auth-btn">编辑按钮 (需要 "edit" 权限)</button>
</div>
<!-- 需要 delete 权限 -->
<div>
<button v-auth="'auth-delete'" class="auth-btn">删除按钮 (需要 "delete" 权限)</button>
</div>
<!-- 需要同时拥有 edit 和 delete 权限 -->
<div>
<button v-auth="['auth-edit', 'auth-delete']" class="auth-btn">高级操作 (需要 "edit" 和 "delete" 权限)</button>
</div>
</section>
</div>
</template>
<script setup>
import { ref, computed } from 'vue';
import { AuthStore } from '@/index';
const authStore = AuthStore();
const newPermission = ref('');
// 获取当前页面的权限列表
const currentPermissions = computed(() => {
return authStore.authButtonList[authStore.routeName] || [];
});
// 添加权限
function addPermission() {
if (!newPermission.value) return;
// 深拷贝当前权限列表
const updatedAuthList = JSON.parse(JSON.stringify(authStore.authButtonList));
// 确保当前路由的权限数组存在
if (!updatedAuthList[authStore.routeName]) {
updatedAuthList[authStore.routeName] = [];
}
// 添加新权限(如果不存在)
if (!updatedAuthList[authStore.routeName].includes(newPermission.value)) {
updatedAuthList[authStore.routeName].push(newPermission.value);
authStore.authButtonList = updatedAuthList;
}
newPermission.value = '';
}
// 移除权限
function removePermission(perm) {
const updatedAuthList = JSON.parse(JSON.stringify(authStore.authButtonList));
if (updatedAuthList[authStore.routeName]) {
const index = updatedAuthList[authStore.routeName].indexOf(perm);
if (index !== -1) {
updatedAuthList[authStore.routeName].splice(index, 1);
authStore.authButtonList = updatedAuthList;
}
}
}
</script>
<style>
.auth-control, .auth-test {
margin-bottom: 30px;
padding: 20px;
border: 1px solid #eee;
border-radius: 4px;
}
.permission-panel {
margin-top: 15px;
}
.permission-list {
margin-top: 10px;
display: flex;
flex-wrap: wrap;
gap: 10px;
}
.permission-tag {
display: inline-flex;
align-items: center;
background: #f2f2f2;
padding: 5px 10px;
border-radius: 4px;
}
.permission-tag button {
background: none;
border: none;
color: #ff4d4f;
cursor: pointer;
margin-left: 5px;
}
.auth-btn {
margin: 10px 0;
padding: 10px 15px;
background: #1890ff;
color: white;
border: none;
border-radius: 4px;
cursor: pointer;
}
</style>🖼️ 效果预览
下图展示了权限指令的实际效果,您可以动态添加或移除权限来观察元素的显示和隐藏:

🔗 与权限系统集成
v-auth 指令会自动从 AuthStore 中获取当前用户的权限数据,无需手动传递。权限数据通常在用户登录后由后端接口返回,并存储在 AuthStore 中。
💡 最佳实践
- 将权限代码按业务模块分类,例如
user-add、report-export - 对安全敏感的操作使用多权限组合,如
['user-delete', 'admin-role'] - 在路由层面也配置相应的权限控制,防止直接访问URL绕过前端权限检查
- 权限名称保持一致性,推荐使用
模块-操作的命名方式