当前位置: 首页 > news >正文

Vue3:自定义指令以及简单的后台管理权限封装

目录

前言:

自定义指令介绍:

局部的自定义指令:

全局自定义指令:

讲讲后台管理权限管理:


前言:

        说起这个自定义指令的使用场景,我第一反应就是,后台管理的权限管理,要问我为什么?就是ruoyi系统用多了😂;本篇就聊聊vue3的自定义指令以及若依的管理权限封装。

        如果对vue指令还是有点懵,不清楚这是vue哪一块的知识,v-if,v-show,v-for总用过吧?没错,指令说的就是它们,这些都是vue内置的指令,同时vue还允许我们注册一些自定义的指令。

自定义指令介绍:

        既然作为指令,当然有它的一些规则,那么指令的规则就是以v字母开头的驼峰变量,当然这是在<script setup>中可以这么写。在没有使用<script setup>的情况下,则是另外一种写法,我会一一进行举例介绍。

借用vue官网的介绍:一个指令的定义对象可以提供几种钩子函数 (都是可选的):

const myDirective = {// 在绑定元素的 attribute 前// 或事件监听器应用前调用created(el, binding, vnode, prevVnode) {// 下面会介绍各个参数的细节},// 在元素被插入到 DOM 前调用beforeMount(el, binding, vnode, prevVnode) {},// 在绑定元素的父组件// 及他自己的所有子节点都挂载完成后调用mounted(el, binding, vnode, prevVnode) {},// 绑定元素的父组件更新前调用beforeUpdate(el, binding, vnode, prevVnode) {},// 在绑定元素的父组件// 及他自己的所有子节点都更新后调用updated(el, binding, vnode, prevVnode) {},// 绑定元素的父组件卸载前调用beforeUnmount(el, binding, vnode, prevVnode) {},// 绑定元素的父组件卸载后调用unmounted(el, binding, vnode, prevVnode) {}
}

指令的钩子会传递以下几种参数:

  • el:指令绑定到的元素。这可以用于直接操作 DOM。

  • binding:一个对象,包含以下属性。

    • value:传递给指令的值。例如在 v-my-directive="1 + 1" 中,值是 2
    • oldValue:之前的值,仅在 beforeUpdate 和 updated 中可用。无论值是否更改,它都可用。
    • arg:传递给指令的参数 (如果有的话)。例如在 v-my-directive:foo 中,参数是 "foo"
    • modifiers:一个包含修饰符的对象 (如果有的话)。例如在 v-my-directive.foo.bar 中,修饰符对象是 { foo: true, bar: true }
    • instance:使用该指令的组件实例。
    • dir:指令的定义对象。
  • vnode:代表绑定元素的底层 VNode。

  • prevNode:之前的渲染中代表指令所绑定元素的 VNode。仅在 beforeUpdate 和 updated 钩子中可用。

局部的自定义指令:

举个例子,想要为元素设置样式。

<template><div v-style>Jay丶萧邦</div>
</template><script setup>const vStyle = (el, binding, vnode, prevNode) => {console.log('el===>', el);console.log('binding===>', binding);console.log('vnode===>', vnode);console.log('prevNode===>', prevNode);}
</script>

 看看都打印的是什么?

 这里的打印值结合上面的说明,就能明白各个值所代表的的意义了。下面我们写成这样

<div v-style="'color:#ff0000;font-size:30px'">Jay丶萧邦</div>

控制的binding将会长这个样子,很显然value是我们传递的值,接下来的工作就是如何把我们传递的value值给当前div,回头一看,el不就是我们的当前绑定的元素吗?

 于是:

	const vStyle = (el, binding, vnode, prevNode) => {console.log('el===>', el);console.log('binding===>', binding);console.log('vnode===>', vnode);console.log('prevNode===>', prevNode);el.style = binding.value}

未采用 <script setup> 的情况,需要使用directives进行注册指令方可!

	export default {setup() {},directives: {// 写在模板上就是v-stylestyle: {mounted(el, binding) {console.log(el, binding);el.style = binding.value}}}}

全局自定义指令:

说到全局自定义指令,第一反应当然是去main.js里面动手脚啊。

所以找到我们的main.js,如下方式:

如此,便是好了!是不是很简单。。。

其实这只是自定义指令最基本的一个用法,里面还有挺多的东西没有列出来,比如arg参数,修饰对象等等,不是我不列,关键是我工作的时候也没用过啊😥

讲讲后台管理权限管理:

说起来后台管理这块,无外乎列表,按钮,表单外加一些统计图。重点在于如何让不同角色的用户登录系统之后,只展示他可以操作的内容,举个最简单的例子-用户管理页面。

大概构成为顶部搜索框,中间是一些操作按钮,比如添加用户,删除用户,修改用户等等,主体那就是用户表格展示用户的信息。我们的重点就放在操作按钮上!

1.基础条件-用户信息存放处

我使用了pinia,不知道pinia怎么使用的去这里=>pinia安装配置,当前登录用户的信息存放在user.js中,当前登录人的name是Jay丶萧邦,拥有添加用户和修改用户的权限,当然这些信息肯定是从后台服务器请求拿来的。

import {defineStore} from "pinia";const userStore = defineStore('userStore', {state: () => ({name: 'Jay丶萧邦',/* 添加用户:system:user:add修改用户:system:user:edit删除用户:system:user:delete导出用户:system:user:export*/permissions: ['system:user:add', 'system:user:edit']})
})export default userStore;

 2.基础条件-操作按钮

	<el-row class="mb-4"><el-button type="primary" plain>添加用户</el-button><el-button type="success" plain>导出用户</el-button><el-button type="info" plain>修改用户</el-button><el-button type="warning" plain>删除用户</el-button></el-row>

2.在你不使用自定义指令的情况下,你该如何去判断哪些操作按钮显示或不显示,首先想到最直接的方式可能是下面这种

<template><el-row class="mb-4"><el-button type="primary" plain v-if="permissions.includes('system:user:add')">添加用户</el-button><el-button type="success" plain v-if="permissions.includes('system:user:export')">导出用户</el-button><el-button type="info" plain v-if="permissions.includes('system:user:edit')">修改用户</el-button><el-button type="warning" plain v-if="permissions.includes('system:user:delete')">删除用户</el-button></el-row>
</template><script setup>import userStore from "@/store/modules/user.js"const permissions = userStore().permissions
</script>

确实能实现,没有毛病,缺点就是每个文件都需要这样写,还有点长,扩展性也不是很好。如今有了自定义指令该怎么写呢?

3.自定义指令v-hasPermi

首先先建这么几个目录文件,directive下的index.js代表我们自定义指令的总入口。

permissions下的index.js代表我们为权限管理这块写的自定义指令。

permissions/index.js

import userStore from "@/store/modules/user.js"const hasPermi = (el, binding) => {const permissions = userStore().permissionsconsole.log(el, binding);
}export default hasPermi;

directive/index.js 

import hasPermi from "./permissions/index.js"function directive(app) {app.directive('hasPermi', hasPermi)
}export default directive;

main.js

index.vue

<el-button type="primary" plain v-hasPermi="['system:user:add']">添加用户</el-button>

缓一缓,看看这些内容能不能看个明白,看看打印值:

说明我们已经通过自定义指令v-hasPermi将值传递进来了,接下来就是拿当前用户的permissions与此值进行比较,之所以写成一个数组,是为了更好的扩展性。

接下来先把操作按钮的权限补充完成

	<el-row class="mb-4"><el-button type="primary" plain v-hasPermi="['system:user:add']">添加用户</el-button><el-button type="success" plain v-hasPermi="['system:user:export']">导出用户</el-button><el-button type="info" plain v-hasPermi="['system:user:edit']">修改用户</el-button><el-button type="warning" plain v-hasPermi="['system:user:delete']">删除用户</el-button></el-row>

再补充点判断条件,permissions/index.js

import userStore from "@/store/modules/user.js"const hasPermi = (el, binding) => {const {value} = binding;const ALL_PERMISSION = "*:*:*";const permissions = userStore().permissions;if (value && value instanceof Array && value.length > 0) {const hasPermission = permissions.some(permission => {return ALL_PERMISSION === permission || value.includes(permission)})console.log(hasPermission);if (!hasPermission) {console.log(el)}} else {throw new Error('请填写当前操作权限值')}
}export default hasPermi;

可以看到,经过一系列的判断,我们已经找到了有哪两个按钮是不用显示的,那就好办了,如何让它们不显示。有人会直接上css,我只能说是有点东西,哈哈哈0.o!

		if (!hasPermission) {console.log(el)el.style.display = 'none'}

 

 那么我这里选择的方式是,把此元素删除掉!

		if (!hasPermission) {console.log(el)el.remove()}

 ok,又是水文的一天!

相关文章:

Vue3:自定义指令以及简单的后台管理权限封装

目录 前言&#xff1a; 自定义指令介绍&#xff1a; 局部的自定义指令&#xff1a; 全局自定义指令&#xff1a; 讲讲后台管理权限管理&#xff1a; 前言&#xff1a; 说起这个自定义指令的使用场景&#xff0c;我第一反应就是&#xff0c;后台管理的权限管理&#xff0c;要…...

剑指 Offer 12. 矩阵中的路径

摘要 剑指 Offer 12. 矩阵中的路径 一、回溯算法解析 本问题是典型的矩阵搜索问题&#xff0c;可使用 深度优先搜索&#xff08;DFS&#xff09; 剪枝解决。 深度优先搜索&#xff1a; 可以理解为暴力法遍历矩阵中所有字符串可能性。DFS 通过递归&#xff0c;先朝一个方向搜…...

springboot+jersey+tomcat实现跨域方式上传文件到服务器

前言 在服务器上&#xff0c;当我们启动了tomcat&#xff0c;就可以以 http://ip地址:8080/文件路径/文件名 的方式&#xff0c;进行访问到我们服务器上处于tomcat的webapps文件夹下的文件 于是为了可以往上面加文件&#xff0c;我们有两种方式&#xff0c;一种就是直接复制文…...

【微信小程序】-- 常用视图容器类组件介绍 -- view、scroll-view和swiper(六)

&#x1f48c; 所属专栏&#xff1a;【微信小程序开发教程】 &#x1f600; 作  者&#xff1a;我是夜阑的狗&#x1f436; &#x1f680; 个人简介&#xff1a;一个正在努力学技术的CV工程师&#xff0c;专注基础和实战分享 &#xff0c;欢迎咨询&#xff01; &#…...

猜数字游戏——C++

我们在有了一定的C基础了以后&#xff0c;简单的实现一个案例&#xff08;其实只要会while循环结构就行了&#xff09;&#xff0c;我们本章内容会实现猜数字游戏&#xff0c;大家有什么语法疑问可以看看我写的&#xff1a;C快速入门_染柒_GRQ的博客-CSDN博客&#xff0c;该博客…...

整数对最小和

题目描述 给定两个整数数组 array1 array2。数组元素按升序排列&#xff0c;假设从array1 、array2中分别取出一个元素可构成一对元素&#xff0c;现在需要取出K个元素并对取出的所有元素求和&#xff0c;计算和的最小值 注意事项 两对元素如果对应于array1 array2中的两个下…...

2023-2-22 -javaagent

周三&#xff0c;天气晴&#xff0c;7度 Java Agent Java Agent也叫作java探针&#xff0c;可以实现动态修改java字节码&#xff0c;完成额外的功能。在java类编译成字节码&#xff0c;在jvm执行之前&#xff0c;它可以读取修改字节码&#xff0c;以来完成额外的功能。 使用…...

JavaScript BOM操作

目录 前言 window 对象 location 对象 navigator 对象 screen 对象 history 对象 前言 BOM&#xff08;Browser Object Model&#xff09;指的是浏览器对象模型&#xff0c;它是 JavaScript 和浏览器之间的接口。通过 BOM&#xff0c;JavaScript 可以与浏览器窗口交互&…...

【机器学习 | 强基计划】开山篇 | 机器学习介绍及其类别和概念阐述

🤵‍♂️ 个人主页: @计算机魔术师 👨‍💻 作者简介:CSDN内容合伙人,全栈领域优质创作者。 机器学习 | 强基计划系列 (一) 作者: 计算机魔术师 版本: 1.0 ( 2022.2.25) 注释:文章会不定时更新补充 文章目录 前言一、机器学习概览1.1 有监督学习和无监督学习1.1.…...

华为OD机试真题Java实现【合规数组】真题+解题思路+代码(20222023)

合规数组 题目 给定一个正整数数组 检查数组中是否存在满足规则的数组组合 规则: A = B + 2C 🔥🔥🔥🔥🔥👉👉👉👉👉👉 华为OD机试(Java)真题目录汇总 ## 输入 第一行输出数组的元素个数 接下来一行输出所有数组元素,用空格隔开 输出 如果存在满…...

BoostSearcher搜索引擎项目

BoostSearcher搜索引擎项目 1.BoostSearcher这个项目是什么&#xff1f; 答&#xff1a;一个为Boost文档建立索引的站内搜索引擎&#xff0c;简单的说就是一个类似于csdn站内文档搜索框。 项目展示&#xff1a; gitee:https://gitee.com/zxlfx/boost-search-engine-project …...

【模拟集成电路】频率综合器(Frequency Synthesizer,FS)设计

应用于无线局域网的频率综合器设计前言频率综合器简介各部分链接链接&#xff1a;前言 本文主要内容是对频率综合器或称为PLL 做出简单介绍&#xff0c;为课程设计部分章节内容&#xff0c;后需给出各部分的设计方案&#xff0c;以及测试结果。 频率综合器简介 无线收发系统中…...

实例8:机器人的空间描述和变换仿真

实例8&#xff1a;机器人的空间描述和变换仿真 实验目的 通过刚体与刚体的平动、转动基础知识的学习&#xff0c;熟悉位姿的描述通过Python编程实践&#xff0c;可视化学习坐标系的变换&#xff0c;熟悉空间变换 实验要求 通过python编程&#xff0c;输入一指定向量和对应的…...

网络 导航

目录内容链接网络网络参考文章&#xff1a;【网络】http请求 调试网络问题解决参考文章&#xff1a;【问题解决】网络 IP DNS解析网络问题解决参考文章&#xff1a;【问题解决】网络 TCP 规则 抓包网络问题解决参考文章&#xff1a;【问题解决】网络 Http请求 调试网络问题解决…...

Web Spider Ast-Hook 浏览器内存漫游-数据检索

文章目录一、资源下载二、通过npm安装anyproxy模块三、anyproxy的介绍以及基本使用1. anyproxy的功能介绍2. anyproxy的基本使用四、给浏览器挂代理五、实操极验demo案例总结提示&#xff1a;以下是本篇文章正文内容&#xff0c;下面案例可供参考 一、资源下载 Github&#x…...

计算机网络笔记、面试八股(二)——HTTP协议

本章目录2. HTTP协议2.1 HTTP协议简介2.2 HTTP协议的优点2.3 HTTP协议的缺点2.4 HTTP协议属于哪一层2.5 HTTP通信过程2.6 常见请求方法2.7 GET和POST的区别2.8 请求报文与响应报文2.8.1 HTTP请求报文2.8.2 HTTP响应报文2.9 响应状态码2.10 HTTP 1.0和1.1的区别2.10.1 长连接2.1…...

docker快速上手使用

文章目录一、docker概述1. 为什么需要docker2. 什么是docker3. docker和虚拟机的区别4. docker三要素二、docker安装1. 添加app源2. 安装docker社区版3. 更换国内docker镜像源三、docker基本使用方法1. 获取镜像2. 查看当前系统中的docker镜像3. 运行docker容器4. 查看当前存在…...

<c++> 类的构造函数与类的析构函数

文章目录类的构造函数什么是构造函数声明和定义构造函数如何使用构造函数默认构造函数类的析构函数什么是析构函数声明和定义析构函数小练习银行账户执行效果类的构造函数 什么是构造函数 Q&#xff1a;什么是类的构造函数 A&#xff1a;构造函数是类的一种特殊成员函数,不需…...

华为OD机试真题Java实现【玩牌高手】真题+解题思路+代码(20222023)

玩牌高手 给定一个长度为n的整型数组,表示一个选手在n轮内可选择的牌面分数。选手基于规则选牌, 请计算所有轮结束后其可以获得的最高总分数。 选择规则如下: 1、在每轮里选手可以选择获取该轮牌面,则其总分数加上该轮牌面分数,为其新的总分数。 2、选手也可不选择本轮…...

Hive Sql整体优化思路

如果遇到sql性能问题&#xff0c;可以先查看4040页面的sql执行信息。一个sql解析为多个stage&#xff0c;一个stage分为多个task。对问题Sql的某一个stage&#xff0c;基本的分析思路如下&#xff1a;所有的task都慢&#xff0c;检查下是否有笛卡尔积(关联字段重复值、关联字段…...

JavaSec-RCE

简介 RCE(Remote Code Execution)&#xff0c;可以分为:命令注入(Command Injection)、代码注入(Code Injection) 代码注入 1.漏洞场景&#xff1a;Groovy代码注入 Groovy是一种基于JVM的动态语言&#xff0c;语法简洁&#xff0c;支持闭包、动态类型和Java互操作性&#xff0c…...

手游刚开服就被攻击怎么办?如何防御DDoS?

开服初期是手游最脆弱的阶段&#xff0c;极易成为DDoS攻击的目标。一旦遭遇攻击&#xff0c;可能导致服务器瘫痪、玩家流失&#xff0c;甚至造成巨大经济损失。本文为开发者提供一套简洁有效的应急与防御方案&#xff0c;帮助快速应对并构建长期防护体系。 一、遭遇攻击的紧急应…...

盘古信息PCB行业解决方案:以全域场景重构,激活智造新未来

一、破局&#xff1a;PCB行业的时代之问 在数字经济蓬勃发展的浪潮中&#xff0c;PCB&#xff08;印制电路板&#xff09;作为 “电子产品之母”&#xff0c;其重要性愈发凸显。随着 5G、人工智能等新兴技术的加速渗透&#xff0c;PCB行业面临着前所未有的挑战与机遇。产品迭代…...

.Net框架,除了EF还有很多很多......

文章目录 1. 引言2. Dapper2.1 概述与设计原理2.2 核心功能与代码示例基本查询多映射查询存储过程调用 2.3 性能优化原理2.4 适用场景 3. NHibernate3.1 概述与架构设计3.2 映射配置示例Fluent映射XML映射 3.3 查询示例HQL查询Criteria APILINQ提供程序 3.4 高级特性3.5 适用场…...

【入坑系列】TiDB 强制索引在不同库下不生效问题

文章目录 背景SQL 优化情况线上SQL运行情况分析怀疑1:执行计划绑定问题?尝试:SHOW WARNINGS 查看警告探索 TiDB 的 USE_INDEX 写法Hint 不生效问题排查解决参考背景 项目中使用 TiDB 数据库,并对 SQL 进行优化了,添加了强制索引。 UAT 环境已经生效,但 PROD 环境强制索…...

2025 后端自学UNIAPP【项目实战:旅游项目】6、我的收藏页面

代码框架视图 1、先添加一个获取收藏景点的列表请求 【在文件my_api.js文件中添加】 // 引入公共的请求封装 import http from ./my_http.js// 登录接口&#xff08;适配服务端返回 Token&#xff09; export const login async (code, avatar) > {const res await http…...

VTK如何让部分单位不可见

最近遇到一个需求&#xff0c;需要让一个vtkDataSet中的部分单元不可见&#xff0c;查阅了一些资料大概有以下几种方式 1.通过颜色映射表来进行&#xff0c;是最正规的做法 vtkNew<vtkLookupTable> lut; //值为0不显示&#xff0c;主要是最后一个参数&#xff0c;透明度…...

【Zephyr 系列 10】实战项目:打造一个蓝牙传感器终端 + 网关系统(完整架构与全栈实现)

🧠关键词:Zephyr、BLE、终端、网关、广播、连接、传感器、数据采集、低功耗、系统集成 📌目标读者:希望基于 Zephyr 构建 BLE 系统架构、实现终端与网关协作、具备产品交付能力的开发者 📊篇幅字数:约 5200 字 ✨ 项目总览 在物联网实际项目中,**“终端 + 网关”**是…...

dify打造数据可视化图表

一、概述 在日常工作和学习中&#xff0c;我们经常需要和数据打交道。无论是分析报告、项目展示&#xff0c;还是简单的数据洞察&#xff0c;一个清晰直观的图表&#xff0c;往往能胜过千言万语。 一款能让数据可视化变得超级简单的 MCP Server&#xff0c;由蚂蚁集团 AntV 团队…...

论文笔记——相干体技术在裂缝预测中的应用研究

目录 相关地震知识补充地震数据的认识地震几何属性 相干体算法定义基本原理第一代相干体技术&#xff1a;基于互相关的相干体技术&#xff08;Correlation&#xff09;第二代相干体技术&#xff1a;基于相似的相干体技术&#xff08;Semblance&#xff09;基于多道相似的相干体…...