对标等保 2.0:Docker 容器安全合规配置的四个核心维度与落地实践

枫少@KillBoy
枫少@KillBoy
枫少@KillBoy
管理员
267
文章
0
粉丝
云原生安全301,373字数 2603阅读8分40秒阅读模式
AI智能摘要
AI 生成的文章内容摘要

不少团队在等保测评整改时会遇到一个尴尬局面:宿主机的加固项一条条都落实了,可测评机构扫到 Docker 环境时,整改单上依然多出一串问题——容器用 root 在跑、daemon 暴露了明文管理端口、镜像来源说不清。等保 2.0(GB/T 22239-2019)并没有给容器单独发一份 checklist,安全计算环境的通用控制点加上云计算、容器安全扩展要求,需要运维自己翻译成 Docker 语言,而翻译的偏差往往就是扣分点。

这篇文章做的就是这个翻译工作。把容器相关的合规要求归纳为"身份可信、镜像可信、运行受控、数据不留痕"四个维度,每个配置项都对应到等保 2.0 的具体控制点,最后汇总成一张可以直接拿去自查的清单。范围只覆盖 Docker 引擎与容器层,不涉及 K8s 集群级别的网络策略。

Docker 容器安全合规四个核心维度示意图:身份可信、镜像可信、运行受控、数据不留痕

身份可信:先管住"谁能碰 Docker"

等保 2.0 安全计算环境下的"身份鉴别"和"访问控制"控制点,落到 Docker 上第一件事是认清一个事实:能访问 Docker daemon 的人,等价于拿到了宿主机 root。因为通过 daemon socket 随时可以启动一个挂载宿主机根目录的特权容器,所以 docker 用户组的成员名单本身就是一份访问控制策略,而不是图方便的授权方式。

具体要做三件事。一是收敛本地访问,把确实需要操作容器的账号加进 docker 组,其余账号一律走 sudo 并保留命令审计记录,定期核对组内是否存在"历史遗留"账号。二是管住远程管理通道,容器安全扩展要求里明确应对容器实例的访问请求进行身份标识和鉴别,并确保使用安全协议连接——确实需要远程管理 daemon 时,必须启用 TLS 双向认证(--tlsverify,走加密的 2376 端口),客户端与服务端互验证书;直接把 tcp://0.0.0.0:2375 这种明文无认证端口暴露在内网,测评时基本就是一条必开的整改项。三是留存操作痕迹,等保的"安全审计"控制点要求审计记录覆盖到每个用户,容器标准同样要求镜像仓库的访问日志保存并定期审查,因此 daemon 操作日志、registry 的推送拉取日志都要集中收集,而不是留在本机随容器生命周期一起消失。

镜像可信:用 cosign 把"来源可查"变成硬约束

等保 2.0 云计算安全扩展要求中专门包含"镜像和快照保护"的内容,容器安全要求也提出应采用密码技术保护容器镜像。翻译过来就是:你要能证明生产环境运行的镜像,就是 CI 构建出来的那一个,中间没被掉包,也不是谁随手 push 上去的。

cosign(Sigstore 项目)是目前最顺手的签名工具,它针对镜像 digest 生成和校验签名。基本链路分三步:

  1. cosign generate-key-pair 生成密钥对,私钥放进 CI 的凭据管理体系,公钥分发给需要部署验证的环境;
  2. CI 构建并推送镜像后执行签名,推荐按 digest 签而不是按 tag 签,避免 tag 被复用后签名指向发生漂移;
  3. 部署前执行 cosign verify 校验签名与公钥,验证不通过就直接拒绝上线。
# CI 中:构建推送后对镜像签名(按 digest)
cosign sign --key cosign.key registry.example.com/app@sha256:9f2c...

# 部署前:验证签名,失败则终止发布
cosign verify --key cosign.pub registry.example.com/app@sha256:9f2c...
使用 cosign 对容器镜像签名并在部署前验证的流程示意

需要注意,签名只是"来源可信"的一半,另一半是镜像内容本身:基础镜像固定到 digest 而不是 floating 的 latest,推入仓库前过一遍漏洞扫描,私有仓库开启访问认证。这些对应的同样是镜像保护条款,测评时会被一并问到。关于容器镜像保护的完整条款背景,可以参考《网络安全等级保护容器安全要求》标准解读

运行受控:禁用 privileged 与细粒度 capability

这是整改中最容易踩坑的部分,对应等保"访问控制"的最小权限原则和"入侵防范"控制点。容器安全扩展要求里有一条写得很直白:应在镜像构建配置文件中将运行用户定义为非最高权限用户,禁止未定义用户或定义为最高权限用户。也就是说 Dockerfile 里必须有明确的 USER 指令,容器内进程不能以 root 运行,评测方法就包括检查 Dockerfile 配置和模拟攻击者利用特权用户控制容器。

USER 只是第一层。即使容器内是非 root 用户,--privileged 一开就前功尽弃:特权容器会拿到全部 linux capabilities 和宿主机设备访问权,容器内 root 与宿主机 root 之间几乎没有边界。合规姿势是全面禁用 privileged 模式,然后用 capability 机制做细粒度授权。linux 把 root 的权限拆成了几十个 capability,例如绑定低端口的 NET_BIND_SERVICE、修改文件属主的 CHOWN 等,Docker 默认会给容器一组相对保守的 capability,但对多数业务来说仍然偏大。稳妥做法是先全部砍掉,再按业务需要逐项加回:

docker run -d 
  --user 10001:10001 
  --cap-drop=ALL 
  --cap-add=NET_BIND_SERVICE 
  --security-opt no-new-privileges:true 
  --read-only 
  registry.example.com/app@sha256:9f2c...

这一条命令同时落实了四个控制点:非 root 运行对应容器扩展的用户要求,--cap-drop=ALL 加按需 --cap-add 对应最小权限,no-new-privileges 防止进程通过 setuid 类机制提权,--read-only 让根文件系统只读、攻击者无法落地工具。在此之上还可以叠加 Docker 默认自带的 seccomp profile,以及内存、PID 数量等资源限制,防止单个容器被攻破后耗尽宿主机资源,这对应"入侵防范"中的资源控制要求。

落地时的现实建议是:先在测试环境用 --cap-drop=ALL 把服务跑起来,观察应用报什么错、实际缺什么能力,再逐项加回。通常一个普通的 Web 服务只需要一两个 capability 就能正常工作,直接照抄网上的权限清单,往往会加回一堆根本用不到的能力。

数据不留痕:敏感数据不残留,审计日志要留存

这个维度对应等保的"数据保密性"要求,以及容器标准中防止镜像内敏感资源被非法访问的条款。它有正反两面,整改时别做反了。

一面是敏感数据不能残留。最常见的事故是密钥进镜像层:构建时 COPY 进去的证书、写在 Dockerfile 里的数据库密码,即使后面用一层 RUN rm 删掉,文件依然躺在历史层里,通过 docker history 或导出镜像就能翻出来。正确姿势是 secret 不进镜像——构建期使用 BuildKit 的 secret mount,运行期通过挂载文件或密钥管理服务注入;用 .dockerignore.git、本地配置挡在构建上下文之外;多阶段构建只把最终产物拷进运行镜像。运行期产生的敏感临时文件用 --tmpfs 挂到内存里,容器停止即消失;数据卷在容器删除后要有明确的清理或归档策略,不能放任残留。

另一面是审计数据必须留存。容器的 stdout 日志、daemon 日志、registry 访问日志要集中外送到日志系统,而不是只存在容器本地。《网络安全法》要求相关网络日志留存不少于六个月,等保测评同样会核查日志的完整性和保存周期。"数据不留痕"指的是敏感业务数据不残留,绝不是把审计痕迹一起抹掉。

落地检查清单

把上面四个维度汇总成一张自查表,每一行都可以直接拿去核对现有环境:

维度检查项合规配置要点对应等保 2.0 要求
身份可信docker 组成员成员最小化,其余操作走 sudo 留痕访问控制
身份可信daemon 远程访问TLS 双向认证,禁用明文 2375 端口身份鉴别与安全协议连接
身份可信操作日志daemon、registry 日志集中收集并定期审查安全审计
镜像可信镜像签名cosign 按 digest 签名,部署前 verify,不过不发布镜像和快照保护
镜像可信镜像内容基础镜像固定 digest,入库前漏洞扫描,仓库开启认证镜像和快照保护
运行受控运行用户Dockerfile 明确 USER,禁止 root 或未定义用户容器扩展-非最高权限用户
运行受控特权模式全面禁用 --privileged访问控制-最小权限
运行受控capabilitycap-drop=ALL 后按业务逐项 cap-add访问控制-最小权限
运行受控提权与文件系统no-new-privileges、read-only、默认 seccomp、资源限制入侵防范
数据不留痕镜像内敏感数据secret 不进镜像层,dockerignore 加多阶段构建数据保密性
数据不留痕运行时敏感数据tmpfs 挂载临时文件,卷有清理归档策略数据保密性
数据不留痕日志留存容器与访问日志外送,留存周期满足法规要求安全审计

建议的使用方式是:先拿这张清单对现有环境做一轮基线自查,标记出不达标项;然后把其中的硬约束——cosign 验签、capability 配置、非 root 运行——直接写进 CI/CD 流水线和部署模板,让合规从"测评前突击"变成"每次发布自动过关"。等测评机构问起来的时候,你能直接拿出配置记录、审计日志和签名验证结果,这比任何口头解释都有说服力。

 
枫少@KillBoy
评论  30  访客  29  作者  1
    • Opal Moonbeam
      Opal Moonbeam 1

      这份清单太及时了,正准备应对等保测评

      • Peace小和平
        Peace小和平 1

        cosign 签 digest 确实比签 tag 稳多了

        • 夜色沉
          夜色沉 0

          之前一直纠结特权容器怎么改,这个方案可行

            • 行路歌
              行路歌 0

              @ 夜色沉 这个方案确实比直接关特权容器更稳妥

            • 深渊咏唱
              深渊咏唱 1

              非 root 运行在某些老镜像里适配起来挺麻烦的

              • 赤焰狂舞
                赤焰狂舞 1

                –cap-drop=ALL 这种做法在生产环境敢直接上吗

                  • Raven_渡鸦
                    Raven_渡鸦 1

                    @ 赤焰狂舞 建议先在灰度环境跑一下 cap-drop=ALL

                  • ForsakenShadow
                    ForsakenShadow 1

                    secret 进镜像层真是大坑

                    • 烟雨红尘
                      烟雨红尘 1

                      终于有人把等保要求翻译成具体的 Docker 参数了

                      • 怨灵之声
                        怨灵之声 1

                        那个 TLS 双向认证的配置细节能再展开说说吗

                          • 蜂蜜小鹿
                            蜂蜜小鹿 1

                            @ 怨灵之声 TLS 配置最关键是证书签发和信任链建立

                          • 比特探秘
                            比特探秘 1

                            多阶段构建确实能有效减少镜像层的敏感信息

                            • 书剑天涯
                              书剑天涯 2

                              感觉把这些写进 CI 流水线才是真正的自动化合规

                              • 软绵绵球
                                软绵绵球 1

                                之前被测评机构卡在 daemon 端口上,得赶紧改

                                • 初音
                                  初音 1

                                  cap-drop=ALL 后按业务加回,这步实操建议太关键了

                                    • 枫少@KillBoy
                                      枫少@KillBoy

                                      @ 初音 是的,默认全禁再按需放开是最稳妥的落地姿势。

                                    • 欢快小云雀
                                      欢快小云雀 1

                                      弱弱问一句,等保测评真的会逐条核对 Dockerfile 里的 USER 指令吗

                                      • 水瓶革新
                                        水瓶革新 1

                                        非 root 用户适配时最好配合 init 进程处理权限

                                        • 烟雨桥
                                          烟雨桥 1

                                          镜像签名加上自动扫描,合规更有保障

                                          • 星照笺
                                            星照笺 0

                                            daemon 日志外送用 fluentd 搞的,稳定半年了

                                            • 绝不服输
                                              绝不服输 1

                                              我们把 checklist 嵌进发布门禁了

                                              • 躺平族
                                                躺平族 0

                                                老服务改造可以先加 no-new-privileges 过渡

                                                • 大炮
                                                  大炮 1

                                                  buildkit 的 secret mount 实践起来很顺

                                                  • 乱码小能手
                                                    乱码小能手 1

                                                    read-only 文件系统对防挖矿真有效

                                                    • 量子撕裂者
                                                      量子撕裂者 1

                                                      等保测评前最怕说不清镜像来源

                                                      • 民谣微风
                                                        民谣微风 0

                                                        私有 registry 开认证后省了不少事

                                                        • 银钩铁画
                                                          银钩铁画 0

                                                          多阶段构建还能缩小镜像体积

                                                          • 曜希奈绪
                                                            曜希奈绪 1

                                                            TLS双向认证配置起来确实麻烦,但测评时确实是硬指标。

                                                            • 脸大如盆子
                                                              脸大如盆子 1

                                                              审计日志留存周期必须明确写进策略

                                                              • 软萌奶盖
                                                                软萌奶盖 1

                                                                cap-drop=ALL 这一步确实容易把服务跑挂,得慢慢加回来。

                                                              匿名

                                                              发表评论

                                                              匿名网友

                                                              拖动滑块以完成验证