3. RBAC 角色分层模型(RBAC1):角色继承与层级设计
RBAC1 在核心模型(RBAC0)的基础上引入了角色继承(Role Hierarchy)机制。这一机制允许角色之间形成上下级关系,子角色自动继承父角色的所有权限,从而显著减少权限配置的重复性,使权限管理更符合真实组织的层级结构。
3.1 角色继承的核心概念
角色继承是指一个角色(子角色)可以继承另一个或多个角色(父角色)所拥有的权限。继承关系通常表现为偏序关系(Partial Order),即满足自反性、反对称性和传递性。
- 父角色(Parent Role):位于层级上方,拥有更通用、更广泛的权限。
- 子角色(Child Role):位于层级下方,继承父角色的权限,并可额外拥有专有权限。
- 继承方向:权限从父角色流向子角色,子角色不能反向继承父角色未拥有的权限。
设计原则:角色继承应遵循“通用权限上浮,专用权限下沉”的原则。将公共操作(如“查看报表”)赋予高层级角色,将特殊操作(如“修改报表模板”)赋予低层级角色。
3.2 角色层级关系设计
角色层级关系通常分为两种结构:树形结构和网格结构。
| 结构类型 | 特点 | 继承规则 | 适用场景 |
|---|---|---|---|
| 树形结构 | 每个子角色只有一个直接父角色,形成单继承链 | 简单、无歧义,权限路径唯一 | 中小型企业、部门职责清晰的组织 |
| 网格结构 | 子角色可以有多个直接父角色,形成多继承 | 复杂,需解决权限冲突(如取并集或按优先级) | 大型集团、跨部门协作频繁的矩阵式组织 |
以下是一个典型的企业级角色层级关系设计示例(树形结构):
3.3 权限向上继承规则
权限向上继承是 RBAC1 的核心机制,其规则可归纳为以下几点:
- 单向继承:权限只能从父角色流向子角色,子角色不能将自己的权限反向赋予父角色。
- 传递性:如果角色 A 继承角色 B,角色 B 继承角色 C,则角色 A 自动继承角色 C 的所有权限。
- 权限并集:子角色的最终权限 = 所有祖先角色的权限并集 + 子角色自身独有的权限。
- 多继承冲突处理:当子角色从多个父角色继承时,若出现权限冲突(如同一操作被赋予不同属性),通常采用“权限并集”或“显式优先级”策略解决。
示例:假设“订单管理员”拥有“查看订单”和“修改订单”权限,“商品管理员”拥有“查看商品”和“上架商品”权限。如果“运营主管”同时继承这两个角色,则“运营主管”将拥有全部四个权限。
3.4 数据表设计(增加角色层级字段)
在 RBAC0 的数据表基础上,RBAC1 需要增加一个表来存储角色之间的继承关系。通常采用邻接表(Adjacency List)或路径枚举(Path Enumeration)方式。以下是最常用的邻接表设计:
-- 角色表(增加 parent_role_id 字段)
CREATE TABLE `sys_role` (
`id` bigint(20) NOT NULL AUTO_INCREMENT COMMENT '角色ID',
`role_name` varchar(64) NOT NULL COMMENT '角色名称',
`role_code` varchar(64) NOT NULL COMMENT '角色编码',
`parent_role_id` bigint(20) DEFAULT NULL COMMENT '父角色ID,NULL表示顶级角色',
`role_level` int(11) DEFAULT 0 COMMENT '角色层级深度(0=顶层,1=第二层,以此类推)',
`status` tinyint(4) DEFAULT 1 COMMENT '状态:0=禁用,1=启用',
`create_time` datetime DEFAULT CURRENT_TIMESTAMP,
`update_time` datetime DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
PRIMARY KEY (`id`),
KEY `idx_parent_role_id` (`parent_role_id`),
CONSTRAINT `fk_parent_role` FOREIGN KEY (`parent_role_id`) REFERENCES `sys_role` (`id`) ON DELETE SET NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='角色表(支持层级继承)';
-- 角色-权限关联表(与RBAC0一致)
CREATE TABLE `sys_role_permission` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`role_id` bigint(20) NOT NULL,
`permission_id` bigint(20) NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_role_perm` (`role_id`, `permission_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='角色权限关联表';
关键字段说明:
| 字段 | 说明 | 示例值 |
|---|---|---|
parent_role_id |
指向父角色的外键,NULL 表示该角色为顶层角色 | 1 |
role_level |
冗余字段,用于快速查询某一层级的角色,避免递归 | 0, 1, 2 |
注意:使用邻接表时,查询某个角色的所有祖先或后代权限需要递归操作。对于深度较大的层级,建议在应用层使用缓存(如 Redis)存储角色继承路径,或使用闭包表(Closure Table)来优化查询性能。
3.5 适用场景分析
RBAC1 角色分层模型特别适用于以下场景:
- 大型企业组织架构:如集团总部→分公司→部门→小组,每一级都有对应的管理角色,权限逐级下放。
- SaaS 多租户系统:平台管理员拥有全局权限,租户管理员继承平台基础权限并拥有租户专属权限。
- 内容管理系统(CMS):总编→栏目主编→编辑→实习编辑,权限从“审核发布”到“仅编辑”逐层细化。
- 金融/医疗行业:合规要求严格,需要明确的权限分级和审计追踪,角色继承可减少权限配置错误。
以下图示展示了 RBAC1 在 SaaS 多租户场景下的权限继承流程:
最佳实践:在实施 RBAC1 时,建议角色层级深度不超过 5 层,以避免权限继承链过长导致性能下降和维护困难。同时,应定期审计角色继承关系,清理冗余或废弃的角色节点。