权限模型:DAC 与 MAC 概念对比、实战中如何选择
聊数据库权限,绕不开两个经典模型:自主访问控制(DAC)和强制访问控制(MAC)。我做了这些年 DBA,几乎每个合规审计项目都会被人问到:“你们到底用的是 DAC 还是 MAC?”“能不能混着用?”
今天我把这两个模型掰开揉碎讲清楚,再聊聊实战里到底怎么选。先上个图,画一下整体关系,后面慢慢展开。
自主访问控制(DAC)—— 谁拥有谁说了算
DAC 的基本思想很简单:数据或资源的拥有者可以自己决定谁有权访问。比如 Linux 系统里文件的所有者可以用 chmod 命令设置 owner/group/other 的读写执行权限。数据库场景下,MySQL 的 GRANT 语句就是 DAC 的典型——你创建了一张表,你就可以 GRANT SELECT 给别人。
我最早做 DBA 时对接过一个业务部门,他们要求「同事间互相开放数据查询权限」。当时就用的 DAC,因为方便啊,表所有者直接授权。结果呢?两个月后一个离职员工居然还能查到新数据——他没被回收权限。这事让我开始警惕 DAC 的权限扩散问题。
强制访问控制(MAC)—— 系统说了算,用户没得选
MAC 就反过来了:安全策略由系统或管理员统一定义,用户不能自行改变访问权限。每个主体(用户、进程)和客体(表、行、列)都被打上安全标签,比如「绝密」「机密」「公开」。只有当主体的标签 >= 客体标签时才能访问,而且主体自己没法改标签。典型实现包括 SELinux、Oracle Label Security、PostgreSQL 的 row-level security 配合标签策略。
我记得在一次银行核心系统合规审查中,甲方要求所有用户权限必须满足「最小权限 + 强隔离」。DAC 根本顶不住,最后上了 Oracle Label Security 的 MAC 模型。那配置是真繁琐,光定义标签层级就折腾了一周。但合规一过,审计方挑不出毛病。
DAC vs MAC 核心对比
我把两者的关键差异列成表格,方便对照选择:
| 维度 | DAC | MAC |
|---|---|---|
| 控制主体 | 对象所有者 / 管理员 | 系统安全策略 |
| 权限粒度 | 通常到对象(表/文件) | 可到行级、列级(标签) |
| 灵活性 | 高,随时授权 | 低,策略修改需重新定义 |
| 安全性 | 依赖人的自觉,易扩散 | 强制约束,防越权能力强 |
| 典型应用 | Linux 文件权限、MySQL GRANT、HDFS ACL | SELinux、Oracle Label Security、PostgreSQL RLS with policy |
| 合规合规度 | 勉强满足基础审计要求 | 满足等保三级/PCI-DSS 强制访问要求 |
| 管理复杂度 | 低,DBA 日常操作 | 高,需专职安全管理员 |
实战中怎么选?—— 我的三条原则
光看概念不够,落地才是硬道理。我根据这些年的踩坑经验,总结了三条选择原则:
1. 先问合规要求有多硬
如果你们公司通过的是等保三级、PCI-DSS、HIPAA 这类强审计,审计方明确要求「强制访问控制」,那不用想,直接上 MAC。DAC 在合规审查里连初筛都过不了。如果只是内部安全自查或等保二级,DAC + RBAC(基于角色的访问控制)基本能扛住。
2. 再看数据敏感度分级
数据已经有分级(公开/内部/机密/绝密)的,MAC 是天然匹配。我有个客户把核心交易数据和配置数据分成了四个安全等级,用 Oracle Label Security 的 MAC 控制,运维人员登录后只能看到自己权限范围内的行——哪怕他拥有全部表的 SELECT 权限也没用。这套东西一旦跑稳了,审计来查数据安全时根本不用慌。
3. 最后评估团队能力
MAC 确实安全,但配置量大、排错难。你们团队有没有专职安全 DBA?如果只有一两个人扛全栈,建议上 DAC + 分层隔离 + 审计日志补充。比如用 MySQL 的 GRANT 做基础,再搭配 ProxySQL 写查询白名单,同时开启 general_log 和审计插件。这样成本低,实战效果也不差。
• 低频核心数据(财务底表、用户隐私) → MAC 强隔离
• 业务日常使用数据(订单、商品) → DAC + RBAC 角色授权
• 开发测试数据(脱敏副本) → DAC 裸授权 + 定期回收
三层配下来,既保住了核心数据的硬安全,又没把运维搞死。
避坑指南:我曾经犯过的错
- 盲目混合模型导致权限混乱。 一次在 MySQL 里同时用 MAC(通过存储过程实现仿标签)又开了 DAC 的 GRANT,结果某用户既通过标签看到了不应该看的行,又因为 GRANT 拥有了删除权限。后来统一策略:MAC 只做行级可见性,DAC 控制对象级 DML。
- 忽视 MAC 的性能开销。 在 PostgreSQL 里加了大量 RLS policy 后,简单查询的 planning time 从 0.2ms 涨到 5ms。批量更新时更明显。后来优化了 policy 表达式,把常用标签直接存储为冗余列,才把开销降下来。
- DAC 下权限回收不及时。 前面提过的离职员工事件。后来我们建了自动化脚本:每月全量扫描数据库中的孤儿权限,一旦发现用户被禁用或离职超过 30 天,自动回收所有 GRANT。
嗯,简单总结一下:DAC 和 MAC 没的好坏,关键看场景。数据安全等级高的、审计严的,优先 MAC;灵活第一、技术团队薄的,DAC + RBAC 再叠审计也能用。别硬搬,更别混用乱了套。
后面章节我会继续讲 RBAC 和 ABAC,两者混合后还能玩出更多花样。今天先到这里,各位 DBA 朋友回去可以看看自家数据库有没有「权限僵尸」——那些从来没被使用过但又一直存在的授权。每清理一个,安全风险就少一分。