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

Vue自定义指令实现点击事件权限拦截控制的npm插件

🎸 把一篇老文章内容 vibecoding 成了 npm 包

以前写过一篇关于「Vue 自定义指令实现按钮权限拦截」的文章。想法挺好,但每次新项目都要从文章里复制代码到 main.ts,总感觉差点意思。

于是最近干脆把它 vibecoding 成了一个正经的 Vue 插件,发到 npm 上了。

原文:基于 Vue 自定义指令实现点击事件权限拦截控制


🤔 为什么需要这个?

大多数项目做到路由权限、接口权限就差不多了,很少有人会细化到按钮点击这个粒度。

但真遇到了就发现有几个痛点:

  • 封装组件不现实 —— 给每个 el-button 包一层 PermissionButton,Props 透传写到手软
  • UI 库不统一 —— Element Plus、Ant Design Vue、Naive UI……换一个就要重新封一套
  • 原生元素也逃不掉 —— <button><div><a>,封起来没完没了

Vue 自定义指令的方案刚好打在痛点上——直接操作原生 DOM 事件,跟 UI 库无关。


🧠 设计思路

插件只做一件事:拦截 click,传给 check,通过就放行,不通过就调 onDeny。

安装时注册 check 函数

app.use(VueInterceptPlugin, {check: (ctx) => userStore.hasPermission(ctx.id),onDeny: (ctx) => {ElMessage.warning(ctx.name,'无权操作')},
})

check 返回 true 放行、false 拦截,判断逻辑完全由你决定——可以从 ctx.el.dataset 读属性,可以从 ctx.value 读原始值,怎么方便怎么来。

两种写法

<!-- 无参数:直接传函数 -->
<el-button v-intercept="handleDelete">删除</el-button><!-- 带参数:数组第一个是函数,后面随便传 -->
<el-button v-intercept="[handleDeleteById, 1001]">删除订单 #1001</el-button>
<el-button v-intercept="[handleDeleteById, 1002, '加急']">删除订单 #1002</el-button>

handler 里只需要写业务逻辑:

const handleDelete = () => { deleteApi() }
const handleDeleteById = (id: number) => { deleteApi(id) }

不传事件对象,参数就是你给的值,不搞隐式追加。

check 可以怎么判断?

check 收到的 ctx 包含 elhandlervalue,想怎么判断都行:

check: (ctx) => {// 从元素属性判断return ctx.el.dataset.role === 'admin'// 从原始值判断(数组传参场景)// const [fn, id, type] = ctx.value// return id !== 1001
}

🔄 Vue 2 / Vue 3 兼容

内部检测 app.version,自动切换指令钩子:

Vue 版本 绑定 更新 卸载
Vue 3 mounted updated unmounted
Vue 2 bind update unbind

一套代码,双平台通用。


🎯 用起来

npm install vue-intercept-plugin
// Vue 3 — main.ts
import { createApp } from 'vue'
import VueInterceptPlugin from 'vue-intercept-plugin'const app = createApp(App)
app.use(VueInterceptPlugin, {check: (ctx) => checkPermission(ctx.el.dataset.perm),onDeny: () => ElMessage.warning('无权操作'),
})
<template><el-buttonv-intercept="handleDelete"data-perm="delete"type="danger">删除</el-button>
</template>

🔧 实现细节

  • WeakMap 存储 —— 元素和事件监听函数的映射存在 WeakMap 里,不污染 DOM,元素销毁后自动回收
  • SSR 安全 —— 检测到 window 不存在时直接跳过,Nuxt 等环境不报错
  • 单元测试覆盖 —— Vitest + jsdom,覆盖权限放行/拦截、数组传参、边界情况等
  • 零依赖 —— 只有 3KB,无外部依赖

💬 最后

  • GitHub: github.com/wangkai000/vue-intercept-plugin
  • npm: npmjs.com/package/vue-intercept-plugin

http://www.jsqmd.com/news/835392/

相关文章:

  • 国补政策2026年最新消息通知:5月第二批国补625亿申领中!618买手机空调电脑家电叠加国补领取入口操作流程一览 - 速递信息
  • 2026年台州黄金回收测评|铂悦名品卖金避坑指南,3家正规品牌实测推荐 - 天天生活分享日志
  • 2026年降AIGC必备指南:实测5款工具,高效降AI,将AI率降至5%以下! - 降AI实验室
  • 2026年榫卯结构家具公司推荐指南/榫卯结构家具生产厂,推荐榫卯结构家具供应,榫卯结构家具生产企业 - 品牌推广大师
  • 让数学公式自动推导
  • 合肥:报考中质协六西格玛黑带和绿带指定报考机构推荐 - 众智商学院课程中心
  • 东莞:报考中质协六西格玛黑带和绿带指定报考机构推荐 - 众智商学院课程中心
  • 长沙:报考中质协六西格玛黑带和绿带指定报考机构推荐 - 众智商学院课程中心
  • 2026年5月18日欧米茄售后服务中心最新电话地址查询 - 速递信息
  • 沈阳:报考中质协六西格玛黑带和绿带指定报考机构推荐 - 众智商学院课程中心
  • 2026发电机励磁过流继电器校验选型指南:专用仪器推荐与核心问题解析 - 速递信息
  • 青岛:报考中质协六西格玛黑带和绿带指定报考机构推荐 - 众智商学院课程中心
  • 2026 太仓黄金回收门店测评|5 家主流门店硬核 PK,闲置金变现不踩坑 - 速递信息
  • Educational Codeforces Round 175 (Rated for Div. 2) C
  • 破解过流继电器校验低效难题:3P现场精准校验方法论如何保障机组安全? - 速递信息
  • 2026年国产雨鞋品牌推荐:不同场景高口碑高性价比雨鞋测评 - 速递信息
  • C++函数式宏的使用注意事项
  • 北京钢筋混凝土检查井厂家实测排行:多维度客观对比 - 奔跑123
  • 《数据基础设施 区域/行业功能节点技术要求》(TC609-6-2025-11)标准规范深度解读
  • 宁波黄金变现流程全记录:从准备到成交,步步为营避坑指南 - 生活测评君
  • 面向程序设计——发布作业集1~3的总结性Blog
  • 2026宁波黄金回收实测:我跑了3家店,终于找到靠谱的 - 生活测评君
  • Postman 测试 API 鉴权成功但代码请求 403 禁止访问为什么?
  • 2026年|论文查重2%但AI率爆表?全网最全降AI率保姆级指南 - 降AI实验室
  • 豫章师范学院就业优势全景报告:数据支撑、产教融合、多元发展 - 寻茫精选
  • 北京钢筋混凝土蓄水池厂家实力排行:品质与服务对标 - 奔跑123
  • 呼和浩特仓库货架选购指南:从市场格局到厂家深度解析 - 品牌推广大师
  • 质量工具学习指南:从理论到落地的转化方法 - 众智商学院职业教育
  • 如何使用 netstat 命令排查服务器是否存在异常对外连接端口?
  • MewUI 项目:面向 NativeAOT 的超轻量级.NET GUI 架构、底层图形管线与性能演进