Frappe v8.7 用户权限模块解析:User Permission DocType 的字段、API 与底层实现

发布时间:2026/9/15 15:22:47

Frappe v8.7 用户权限模块解析:User Permission DocType 的字段、API 与底层实现 Frappe v8.7 用户权限模块解析User Permission DocType 的字段、API 与底层实现【免费下载链接】frappeLow code web framework for real world applications, in Python and Javascript项目地址: https://gitcode.com/GitHub_Trending/fr/frappe导读本文基于 Frappe 框架变更日志 frappe/change_log/v8/v8_7_0.md 中 v8.7.0 的核心更新——User Permission is now a DocType——展开讲解。该版本把用户权限从原先零散的管理入口收敛为一个独立的文档类型DocType并提供了全新的录入界面用于替代原有的 Role / User Permission 管理器。读完本文你将掌握 User Permission 文档的每个字段含义、前端录入与批量操作的完整流程、后端frappe.permissions的鉴权链路以及嵌套树、默认值、按 DocType 适用范围等高级用法能够直接在自己的 Frappe 站点上配置并验证基于文档级的行级数据隔离。一、v8.7 更新背景为什么把 User Permission 变成 DocType1.1 变更日志原文v8.7.0 的变更日志frappe/change_log/v8/v8_7_0.md全文如下User PermissionsUser Permission is now a DocType, a new UX for the existing Role and User Permission managers to make it easy to enter permissions. For more details please check User Permissions从源码结构看这次变更的落地方式是在 Core 模块下新增User PermissionDocType 的完整四件套——元数据定义JSON、后端控制器Python、表单脚本与列表视图脚本JavaScript——让给某用户开放某文档的访问权这件事从硬编码逻辑变成可查询、可导入、可审计的普通数据记录。1.2 这一变更带来的能力提升将用户权限实体化成为 DocType后获得的能力包括可批量维护支持allow_import可通过 CSV 导入批量创建权限记录见 user_permission.json可审计追踪track_changes开启任何权限变更都有时间戳与操作者记录可编程操作后端暴露了add_user_permissions、clear_user_permissions等白名单 API可被前端对话框或脚本调用权限本身可被权限控制只有System Manager角色拥有该 DocType 的完整读写权限见 user_permission.json。二、User Permission DocType 字段全景User Permission 的完整字段定义位于 frappe/core/doctype/user_permission/user_permission.json。核心字段如下表字段名字段类型是否必填说明userLink (User)是被授予权限的用户建立了搜索索引用于快速按用户检索allowLink (DocType)是允许访问的文档类型DocType表单中过滤掉 Single 与 Table 类型for_valueDynamic Link是具体允许访问的文档记录动态链接到allow指定的 DocTypeis_defaultCheck否标记该记录为默认权限影响新建文档时默认值的选取apply_to_all_doctypesCheck否默认勾选是否将该权限应用到所有相关 DocTypeapplicable_forLink (DocType)条件必填仅当应用到所有 DocType未勾选时必填指定权限实际生效的 DocTypehide_descendantsCheck否默认隐藏对树形Nested SetDocType 生效勾选后隐藏指定节点的所有后代2.1 字段间的联动约束allow只能选择普通 DocType表单脚本通过set_query(allow, ...)过滤issingle: 0且istable: 0见 user_permission.jsapplicable_for的候选列表来自get_applicable_for_doctype_list白名单接口user_permission.py它基于get_linked_doctypes找出与allow所选 DocType 有关联的所有 DocType再补充当前 DocType 本身勾选应用到所有 DocType时会自动清空applicable_for并且前端将其改为必填/隐藏联动user_permission.jshide_descendants仅在allow属于 Nested Set树形DocType 时显示判断依据是frappe.boot.nested_set_doctypesuser_permission.js。三、数据校验与缓存失效后端控制器的核心逻辑User Permission 的后端控制器在 frappe/core/doctype/user_permission/user_permission.py 中UserPermission类继承Document。3.1 保存时的双重校验validate保存含插入任何 User Permission 记录时都会执行两步校验重复记录校验validate_user_permission按user allow for_value applicable_for apply_to_all_doctypes组合查重命中则抛出DuplicateEntryErroruser_permission.py默认值重叠校验validate_default_permission若本记录勾选了is_default则检查同一用户、同一allow下是否已存在其他默认记录含应用到所有 DocType的记录存在则拒绝保存防止同一 DocType 出现两个默认值user_permission.py。3.2 变更后的缓存与实时同步on_update与on_trash中执行两件事user_permission.pyfrappe.cache.hdel(user_permissions, self.user)删除该用户在 Redis 中的权限缓存frappe.publish_realtime(update_user_permissions, userself.user, after_commitTrue)事务提交后通过 WebSocket 通知前端刷新该用户的权限状态保证多端登录下权限即时生效。3.3 权限读取与缓存构建get_user_permissions(user)user_permission.py是整条鉴权链的数据源头Administrator与Guest直接返回空字典不受用户权限约束优先从frappe.cache.hget(user_permissions, user)读取缓存未命中时遍历该用户的所有 User Permission 记录按allow分组聚合每条记录以{doc, applicable_for, is_default, hide_descendants}形式存入树形扩展若allow对应的元数据是 Nested Setmeta.is_nested_set()且未勾选hide_descendants会通过frappe.db.get_descendants把该节点的所有后代文档也加入允许列表结果写入frappe.cache.hset(user_permissions, user, out)供后续请求复用捕获SQLError中的表不存在异常以兼容 patch 升级场景。另外send_user_permissions(bootinfo)会在登录启动阶段把当前用户权限注入bootinfo.user[user_permissions]前端据此渲染get_current_user_permissions则以白名单接口形式返回当前登录用户的权限user_permission.py。四、鉴权引擎has_user_permission 如何消费 User Permission用户权限最终在 frappe/permissions.py 的has_user_permission(doc, user, ...)frappe/permissions.py中生效其判断分两步STEP 1 —— 检查文档自身若user_permissions中存在该文档的 DocType则比对文档 name 是否在允许列表中树形 DocType 创建场景则沿父节点向上回溯匹配并参考各节点的hide_descendants标记。STEP 2 —— 检查所有 Link 字段遍历文档含子表行的全部 Link 字段若字段指向的 DocType 存在用户权限规则则校验字段值是否在允许集合内空值在非严格模式下放行。被拒绝时会给出精确报错信息例如You are not allowed to access this {0} record because it is linked to {1} {2} in row {3}, field {4}frappe/permissions.py方便定位是哪个字段、哪一行引发拦截。4.1 严格模式开关鉴权行为受系统设置apply_strict_user_permissions控制字段定义于 frappe/core/doctype/system_settings/system_settings.json开启后Link 字段为空值也会被校验新建未保存文档在read/write操作下同样适用关闭默认时空 Link 字段跳过校验Single 文档类型永远不应用严格模式因为其内含大量空 Link 字段。4.2 默认值辅助get_permitted_documents(doctype)与filter_allowed_docs_for_doctypefrappe/permissions.py会把is_default标记的记录排在允许列表最前供新建文档时自动填入默认值使用——这正是test_default_user_permission所验证的行为给某用户配置了 Blog Category 的默认权限后新建 Blog Post 时其分类字段会自动取默认值。五、前端体验表单、批量对话框与快捷操作5.1 表单视图frappe/core/doctype/user_permission/user_permission.js 在表单页提供allow/applicable_for的动态查询过滤见 2.1一个自定义按钮View Permitted Documents点击后跳转到Permitted Documents For User报表并带入当前用户作为过滤条件user_permission.js。5.2 列表视图的Add / Update对话框frappe/core/doctype/user_permission/user_permission_list.js 在列表页注入了两个高效入口Add / Update添加/更新弹出对话框依次选择用户 → DocType → 具体文档再选择是否应用到所有 DocType、是否设为默认、是否隐藏后代以及取消全部应用后勾选具体的 Applicable DocTypes 多选列表。提交时调用后端白名单方法frappe.core.doctype.user_permission.user_permission.add_user_permissions返回1表示创建/更新成功0表示无变化。该接口内部自动处理三种场景的原子切换user_permission.py从应用到所有切换到部分 DocType先删除原有的全部应用记录再为选中的每个 DocType 分别创建applicable_for记录从部分 DocType切换到全部应用删除所有applicable_for记录创建一条apply_to_all_doctypes1的记录保持不变直接返回 0。Bulk Delete批量删除按用户 DocType两个条件一键清空该用户在该 DocType 上的全部权限调用clear_user_permissions接口并反馈删除条数user_permission_list.js删除后frappe.clear_cache()确保立即生效。六、编程式用法通过 API 维护权限除界面操作外可以在代码或 Console 中直接调用以下白名单接口均要求System Manager角色接口作用add_user_permissions(data)传入{user, doctype, docname, is_default, apply_to_all_doctypes, applicable_doctypes, hide_descendants}按第四节所述逻辑创建/更新权限user_permission.pyclear_user_permissions(user, for_doctype)删除指定用户在某 DocType 上的全部权限返回删除条数user_permission.pycheck_applicable_doc_perm(user, doctype, docname)查询某权限目前作用于哪些 DocTypeuser_permission.pyget_current_user_permissions()获取当前登录用户的全部权限user_permission.pyPython 侧通用辅助函数非白名单from frappe.core.doctype.user_permission.user_permission import ( get_user_permissions, # 获取指定用户默认当前用户的权限字典 user_permission_exists, # 判断相似权限是否已存在 get_permitted_documents, # 获取当前用户在指定 DocType 上被允许的文档列表 ) from frappe.permissions import has_user_permission # 判断用户是否可访问某文档权限结构示例get_user_permissions的返回值按 DocType 分组{ Customer: [ {doc: CUST-00001, applicable_for: Sales Order, is_default: 0, hide_descendants: 0}, {doc: CUST-00002, applicable_for: None, is_default: 1, hide_descendants: 0}, ] }七、测试用例验证行为与边界User Permission 的功能由 frappe/core/doctype/user_permission/test_user_permission.py 覆盖主要场景包括默认值唯一性test_default_user_permission_validation验证同一用户同一 DocType 下重复创建默认权限会抛出ValidationError新建文档取默认值test_default_user_permission验证配置默认权限后用户新建文档时关联字段自动填入默认值全部应用 ↔ 部分应用的切换test_for_apply_to_all_on_update_from_apply_all、test_for_applicable_on_update_from_apply_to_all等用例验证两种模式互转时记录的增删行为部分转全部会删除所有applicable_for记录全部转部分会删除apply_to_all_doctypes记录嵌套树后代可见性test_user_perm_for_nested_doctype在树形 DocTypePerson上验证给父节点授权后子节点默认可见has_user_permission返回 True勾选hide_descendants后子节点立即不可见权限作用域隔离test_user_perm_on_new_doc_with_field_default验证在无关 DocType 上创建的权限不会影响其他 DocType 新建文档的默认值行为。这些用例同时验证了has_user_permission位于 frappe/permissions.py与get_user_permissions的完整链路是理解本文所述机制的可靠参照。八、实践建议与注意事项先角色权限、后用户权限User Permission 属于行级记录级数据过滤它叠加在角色权限之上用户仍需通过角色获得对应 DocType 的读/写权限User Permission 负责进一步缩小可见范围合理使用应用到所有 DocType默认勾选意味着该权限会作用于所有关联 DocType若只想限定某个业务场景如仅对 Sales Order 生效务必取消勾选并指定applicable_for善用默认权限为常用文档设置is_default可减少新单据录入时的选择成本但注意每个用户在每个 DocType 上只能有一个默认记录树形 DocType 的可见性对树形数据如账户科目、部门授权父节点会默认包含后代如需隐藏后代请勾选hide_descendants权限变更即时生效修改权限后缓存与前端实时状态会自动刷新无需重启服务但若通过 CSV 导入权限导入完成后建议手动执行一次frappe.clear_cache()。小结从 v8.7.0 起User Permission 在 Frappe 框架中正式成为一等公民 DocType其字段设计user/allow/for_value/is_default/apply_to_all_doctypes/applicable_for/hide_descendants与配套的缓存、校验、实时同步机制共同构成了框架级的行级数据权限方案。本文围绕变更日志这一入口结合 user_permission.json、user_permission.py、permissions.py 及对应测试文件完整还原了该特性的字段含义、前端操作、后端 API 与鉴权原理可作为在 Frappe 站点上配置与二次开发用户权限的实战参考。【免费下载链接】frappeLow code web framework for real world applications, in Python and Javascript项目地址: https://gitcode.com/GitHub_Trending/fr/frappe创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
延伸阅读

更多相关文章

2026/9/15 15:22:47

Hydra 插件开发指南:从注册机制到自动发现与实战落地

Hydra 插件开发指南:从注册机制到自动发现与实战落地 【免费下载链接】hydra Hydra is a framework for elegantly configuring complex applications 项目地址: https://gitcode.com/GitHub_Trending/hyd/hydra 导读 本文以官方插件开发文档 website/docs/…

2026/9/15 15:17:46

ML-KNN多标签学习算法详解:从贝叶斯后验概率到Python实践

如果你在业务里碰到这种任务:一篇文章同时属于“科技”和“互联网”,一张图里既有“人”又有“车”,一首歌的情感标签是“快乐”但又带一点“激动”——这种任务再硬拆成多个二分类往往效果很一般,因为它们本质上是多标签学习&…

2026/9/15 15:17:46

小样本物体检测实战指南:从原理到工业落地

1. 什么是小样本物体检测:不是“数据少就叫小样本”,而是“少得有讲究”小样本物体检测(Few-Shot Object Detection,FSOD)这个词最近在CV圈里频繁刷屏,但很多人一听到“小样本”,下意识就觉得是…

2026/9/15 15:27:48

SequencePlayer

SequencePlayer 【免费下载链接】iii Effortlessly compose, extend, and observe every service in real-time for the first time ever. 项目地址: https://gitcode.com/GitHub_Trending/mo/iii kind: archetypeimport: import { SequencePlayer } from lib/component…

2026/9/15 15:27:48

AI辅助内存优化实战:旧笔记本从94%占用降到64%

先坦白一下背景:手头这台用了快五年的旧笔记本,8GB内存,平时也就开几个浏览器标签页、挂着微信、偶尔跑个IDEA写写代码,结果任务管理器一打开,内存占用常年稳定在94%,风扇基本没停过,切窗口都能…

2026/9/15 15:27:48

RAG技术解析:从原理到电商搜索实战应用

1. RAG技术为何成为程序员必备技能最近半年,我身边至少有20位技术主管在团队内推行RAG技术落地。上周一位做电商搜索的同行告诉我,他们用RAG方案将客服响应准确率从63%提升到了89%。这种技术正在以惊人的速度改变着人机交互的方式。RAG(Retri…

2026/9/15 15:22:47

HFSS仿真边界条件与激励方式设置指南:从原理到实操

1. 边界条件和激励方式:HFSS仿真结果的两大命门很多刚接触HFSS的朋友都有过这种经历:模型建得没有问题,网格剖分也挺顺利,仿真跑完之后一看结果,谐振频率偏了百分之十几,或者S11曲线平得跟一条直线似的&…

2026/9/15 4:54:30

拯救者Y7000黑屏故障排查与维修实战指南

1. 项目概述:一台黑屏的拯救者Y7000,到底卡在哪一步? 联想拯救者Y7000系列笔记本,从2018年第一代搭载i5-8300H开始,到后来的i7-9750H、i7-10750H、i5-11400H,再到2023年款的R7-7840HS,它始终是学…

2026/9/15 0:01:16

AI英语单词APP开发:自适应学习算法与移动端优化实践

1. 项目概述 作为一名在移动应用开发领域摸爬滚打多年的老手,我最近完成了一个AI英语单词APP的开发项目。这个项目将传统单词记忆方法与现代AI技术相结合,打造了一款能够智能适应不同用户学习习惯的英语学习工具。 市面上大多数单词APP都存在一个通病&a…

2026/9/15 0:01:16

Flutter与OpenHarmony结合开发手语学习APP实战

1. 项目背景与核心价值作为一名同时接触过Flutter和OpenHarmony的开发者,最近我完成了一个基于Flutter for OpenHarmony的手语学习APP实战项目。这个项目最大的特点在于实现了跨平台框架与国产操作系统深度结合的创新实践——用Flutter开发的应用能完美运行在OpenHa…

2026/9/15 0:01:16

六个月成为机器人工程师:从ROS2到SLAM的实战路径

1. 六个月的紧迫感从哪来:先搞清楚你要成为哪种机器人工程师说实话,六个月的期限并不是一个宽松的时间线。市面上任何一本正经的机器人学教材都超过五百页,ROS2的官方文档可以翻到你怀疑人生,再加上ABB、KUKA这些工业机器人厂家动…

2026/9/15 14:22:53

USB Type-C PCB布局分区设计:电源、高速信号与PD协议全攻略

做硬件这行,Type-C接口算是典型的“看着简单,做起来全坑”的东西。光引脚就24个,高低速信号、电源、控制线全部塞在一个小小的连接器里,如果PCB布局不做规划,打样回来基本就是“插上没反应”、“高速掉线”、“静电一打…

2026/9/14 13:53:59

系统编程学习原型如何补齐稳定性边界

系统编程学习原型如何补齐稳定性边界预算有限时&#xff0c;我先优化明显多余的复制&#xff0c;而不是猜测性地换容器。用借用传递只读数据通常就能减少分配&#xff1a; fn parse(line: &str) -> Result<Item, Error> { /* ... */ }用基准确认热点确实在分配&am…

2026/9/15 11:42:23

雨花区哪家财务公司代理记账比较好?

在雨花区&#xff0c;企业处理财税事务常常面临诸多挑战&#xff0c;选择一家靠谱的财务公司至关重要。湖南巨勤财务管理咨询有限公司就是本地正规实体财税服务机构&#xff0c;深耕本地工商财税行业多年&#xff0c;熟悉当地工商局、税务局最新政策与申报流程。主营公司注册、…

还想了解更多?直接咨询顾问

免费诊断 + 免费方案 + 透明报价。

全国咨询热线400-8866-253
免费获取方案
咨询二维码