核心是写准deny规则、覆盖挂载路径、显式加载绑定策略:用deny /etc/ rwklx等递归禁止敏感路径,补充deny /host/data/ rwklx覆盖挂载点,通过apparmor_parser加载后以--security-opt指定策略名生效。

配置 AppArmor 为 Docker 容器定制细粒度的文件权限隔离策略,核心在于**写准 deny 规则、覆盖挂载路径、显式加载并绑定策略**。不是靠“加白名单”,而是靠“精准封黑点”——因为默认的 docker-default 策略本身已放行大量基础路径,盲目添加 allow 容易遗漏或引发冲突。
明确拒绝敏感宿主机路径(关键第一步)
在自定义 profile 中,用 deny 语句直接封锁高风险目录,必须带递归通配符 /**,否则规则无效:
-
deny /etc/** rwklx,—— 阻止读、写、链接、锁定、执行,覆盖/etc/shadow等深层文件 -
deny /boot/** rwklx,—— 防止篡改引导配置 -
deny /root/** rwklx,—— 封锁管理员主目录 -
deny /proc/sys/** w,和deny /sys/** w,—— 禁止修改内核参数(如net.ipv4.ip_forward)
注意:deny /etc/(不带 **)仅匹配目录自身,/etc/passwd 仍可被访问,务必补全。
覆盖容器内挂载点对应的真实宿主机路径
Docker 使用 -v /host/data:/app/data 时,AppArmor 检查的是进程视角下的**实际路径映射**。若容器内操作 /app/data/file.txt 被拒,问题往往出在 profile 未覆盖宿主机的 /host/data/:
- 在 profile 中添加
deny /host/data/** w,或更严格地deny /host/data/** rwklx, - 若挂载路径动态变化(如通过环境变量),建议统一约束父级目录,例如
deny /host/** rwklx, - 避免只限制容器内路径(如
/app/data),AppArmor 不按容器命名空间解析路径
加载策略并绑定到容器启动过程
Docker 不会自动识别新 profile,必须分两步完成:
- 用
apparmor_parser -r /etc/apparmor.d/container-restrict加载策略(-r支持重复加载) - 运行容器时指定策略名:
docker run --security-opt apparmor=container-restrict ...(注意:是 profile 名,不是文件路径) - 验证是否生效:
docker exec -it <cid> cat /proc/self/attr/current</cid>,输出应含container-restrict (enforce) - 若提示
profile not found,检查 profile 首行profile container-restrict是否匹配,以及语法是否完整(每条规则以逗号结尾)
基于最小权限原则精简允许项(可选增强)
在 deny 基础上,可进一步收紧默认放行项。例如,默认 docker-default 允许 /dev/pts/*,但若容器无需伪终端,可显式禁止:
deny /dev/pts/** rw,-
deny /run/systemd/** r,(禁读 systemd 运行时状态) - 对只读挂载卷,用
/data/** r,替代宽泛的/data/** rw,,再配合deny /data/** w,双重保险
所有规则需置于 profile 的主体块内,且位于 include <tunables></tunables> 之后、capability 声明之前。











