Sun Blog

Back

基于 RBAC 的权限模型优化实践Blur image

传统 RBAC(Role-Based Access Control)模型在企业系统中被广泛应用,但在复杂业务场景下容易出现 「角色爆炸」 问题。本文在经典 RBAC 的基础上,引入 用户级 Allow / Deny 覆盖机制,并结合 Bitmask 位掩码 优化权限存储与鉴权性能,实现 API 级细粒度控制,满足多业务线、复杂授权场景下的权限管理需求。

RBAC 权限模型简介#

RBAC(Role-Based Access Control,基于角色的访问控制)是一种通过 「角色」 来组织和管理权限的访问控制模型。其核心思想是:用户不直接拥有权限,而是通过角色间接获得权限

这种设计将「用户」和「权限」解耦,大幅提升了权限管理的可维护性。

核心组成#

典型 RBAC 模型包含以下几个核心概念:

  • User(用户) :系统的使用者,如管理员、员工、主管等;
  • Role(角色) :权限的集合,是权限的载体;
  • Permission(权限) :系统允许执行的具体操作(如访问某个 API、执行某个按钮操作等)。

数据库模型设计#

标准 RBAC 的数据库模型通常包括:

  • user
  • role
  • permission
  • user_role 表(用户与角色,多对多)
  • role_permission 表(角色与权限,多对多)

关系结构如下:

User  <--->  User_Role  <--->  Role  <--->  Role_Permission  <--->  Permission
plaintext

 优缺点#

RBAC 模型的优点是权限分配清晰、管理结构规范,维护成本较低且用户与权限解耦

缺点是当某个用户需要「特殊权限」,需要给该用户单独新增一个角色,久而久之角色数量呈指数级增长,这就是所谓的 「角色爆炸」

优化方案设计#

为了解决角色爆炸问题,并提升权限系统性能,本文在 RBAC 基础上做了两点核心优化:

  1. 引入用户级 Allow / Deny 覆盖机制
  2. 使用 Bitmask 位掩码优化权限存储与鉴权计算

引入用户级 Allow / Deny 覆盖机制#

在保留原有 RBAC 模型的前提下,新增一张 user_permission 表,用于记录用户级别的权限覆盖。

该表支持两种类型:

  • Allow(允许)
  • Deny(拒绝)

当某个用户需要特殊权限时,无需新增角色,只需在 user_permission 表中新增一条记录,即可实现对角色权限的局部覆盖。

最终权限可通过以下规则计算:

最终权限 = (角色权限 ∪ 用户Allow) - 用户Deny
plaintext

这样既保留了 RBAC 的结构优势,又解决了「角色爆炸」问题。

使用 Bitmask 优化权限存储与鉴权性能#

在 API 级细粒度权限控制场景下,如果每个用户和 API、角色和 API 都单独存储一条权限数据,会产生庞大的数据量,为此,引入 Bitmask 进行优化。

将某个模块下的所有 API 权限映射为一个 64 位整数:

  • 默认值为 0
  • 每一位代表一个 API 权限
  • 若允许访问,则将对应位置为 1

例如:

第 0 位 -> 查询接口
第 1 位 -> 新增接口
第 2 位 -> 删除接口
...
plaintext

一个角色或用户在某模块下的所有权限,仅需一个 BIGINT 字段存储,一行数据即可表示完整权限集合,大幅降低存储空间占用

在实际鉴权时流程如下:

  1. 从拦截器中获取当前 API 的 URL
  2. 解析其对应模块及位序号
  3. 计算用户最终权限掩码 finalMask= (roleMask | userAllowMask) & ~uerDenyMask
  4. 判断对应位是否为 1

核心逻辑示例:

boolean hasPermission = (finalMask & (1L << apiIndex)) != 0;
java

整套鉴权逻辑仅通过位运算完成,无需多表 join,无需大量权限比对,时间复杂度接近 O(1)。

扩展:ABAC 权限模型#

ABAC(Attribute-Based Access Control,基于属性的访问控制)是一种基于 「属性 + 策略规则」 进行动态授权的权限模型。

其核心思想是:是否允许访问,取决于「你是谁 + 你在什么场景 + 访问什么资源 + 满足什么规则」。

ABAC 权限模型是一种更灵活、更细粒度、更动态的权限控制模型。

ABAC 的核心组成#

ABAC 的决策基于四类属性:

  • 用户属性:描述访问者本身的属性;
  • 资源属性:描述被访问对象的属性;
  • 环境属性:描述当前访问环境,例如访问时间、IP 地址;
  • 操作属性:描述执行的动作。

ABAC 的决策方式#

ABAC 的核心是用策略定义一组规则,当属性满足规则时才允许访问。

例如,允许访问的条件:

用户.department == 资源.department
AND
资源.level != "机密"
AND
当前时间 在 9:00 - 18:00
java

如果全部条件满足则允许访问,否则拒绝访问。

ABAC 的优缺点#

ABAC 具有极强的灵活性,支持数据级权限控制,支持上下文感知(IP/权限),天然适合多组织多租户系统,但是实现复杂、策略管理困难、性能压力较大、规则冲突处理复杂。

基于 RBAC 的权限模型优化实践
https://blog.csun.site/blog/2025-07-27-rbac-permission-model-optimization-allow-deny-bitmask
Author Sun Xin
Published at July 27, 2025
Comment seems to stuck. Try to refresh?✨