课题研究 云安全与容器安全 子课题03 · 第07页 / 共8页
03子课题 · 云原生软件供应链与镜像安全

云原生软件供应链与镜像安全第07页:CI/CD流水线凭证与第三方Action安全

CI/CD流水线是供应链中"权限密度最高、攻击ROI最大"的环节。本页建立凭证治理基线(OIDC工作负载身份联邦,GitHub Actions 2021年10月上线),系统解析PPE(毒化流水线执行,Cider Security 2022)两类形态,深度复盘2025年3月tj-actions/changed-files事件(CVE-2025-30066,约2.3万个仓库,CISA KEV收录)的根因链条与响应清单,并给出自托管Runner风险基线、Secrets管理与流水线安全核查清单。

OIDC联邦PPECVE-2025-30066第三方Action固定自托管RunnerSecret Scanning研究状态:研究中
本页定位流水线治理层:凭证、第三方依赖与执行环境
核心事件tj-actions/changed-files(2025-03,CVE-2025-30066,KEV收录)
输出物OIDC迁移基线、PPE防护清单、事件响应清单

01 · 凭证风险面:从长期令牌到工作负载身份

流水线是组织内权限密度最高的系统:源码读写、制品发布、云资源管理、密钥签名往往集中于同一执行环境。传统做法——生成长期Access Key写入CI变量——意味着任何一次脚本注入或日志泄露都等价于长期失陷(Codecov 2021、Docker Hub 2019的共性教训)。现代基线是OIDC工作负载身份联邦:

模式机制风险对比
长期静态令牌云Access Key/ PAT写入CI Secrets,长期有效泄露窗口=有效期全周期;跨仓库复制扩散难追踪;无法精细绑定调用者身份
OIDC联邦(推荐基线)CI运行时向IdP换取短期JWT(绑定仓库/分支/工作流),云侧角色按token条件授权(GitHub Actions于2021年10月上线OIDC支持;GitLab、Buildkite等随后跟进)令牌分钟级过期、调用身份精确绑定、无需在CI存储任何云凭证——静态凭证面趋零

落地要点:① 云侧角色信任策略必须校验token的iss/sub/aud与仓库分支组合,防止“任意分支工作流冒领生产角色”;② 环境(Environment)保护规则+必需评审人,把生产发布权限从“能运行流水线”中分离;③ 轮换剩余存量令牌并启用泄露检测(GitHub Secret Scanning、云厂商凭证监控)。

02 · PPE:毒化流水线执行

PPE(Poisoned Pipeline Execution)由Cider Security于2022年系统化提出,并已被OWASP纳入CI/CD安全Top 10(CICD-SEC-4:Poisoned Pipeline Execution),指攻击者无需直接攻陷构建基础设施,而是通过修改流水线定义或输入,使流水线执行恶意步骤。两类形态:

形态机制示例
Direct PPE直接修改仓库内流水线配置文件(.github/workflows/*.yml)触发恶意步骤Fork PR篡改workflow后由pull_request_target等事件在目标上下文执行
Indirect PPE流水线配置未改,但引用的脚本/配置/标签被篡改,执行时代码变更tj-actions/changed-files标签重指(2025年3月,CVE-2025-30066):恶意commit混入后,在开启debug日志的workflow中将密钥打印进日志

2.1 tj-actions事件深度复盘(2025年3月,已核实要素)

  • 时间线:2025年3月14—15日,该Action的v1—v45.0.7标签被重指向含恶意提交的commit(公开记录的恶意commit哈希为0e58ed8);3月18日CISA将其纳入KEV目录(CVE-2025-30066,CVSS 8.6);关联事件reviewdog/action-setup(CVE-2025-30154)手法相同;
  • 影响规模:GitHub平台数据与多家安全机构分析显示约2.3万个公开仓库使用该Action;恶意代码将ACTIONS_*等敏感环境变量(含密钥)写入workflow日志,日志可被具有读取权限者查看;
  • 根因链条:后续调查(StepSecurity)显示攻击起点为@tj-actions-bot账号的个人访问令牌(PAT)被攻陷;标签可变引用(未固定commit SHA)+ workflow默认将fork PR上下文中的敏感变量带入日志——两个“低危惯例”叠加成高危事件;
  • 防御基线:第三方Action固定到完整commit SHA(而非tag);最小化打印进日志的变量范围;对workflow日志开启密钥遮蔽并限制读取权限;定期审计Actions依赖树。

2.2 事件响应清单(此类事件通用)

动作要点
立即隔离锁定受影响workflow运行记录与日志访问;暂停使用受影响Action版本
凭证轮换假设所有出现在日志中的密钥已泄露:云角色、注册中心令牌、签名密钥全量轮换并审计使用记录
溯源排查检查恶意commit进入路径(上游账号/标签机制);评估构建产物是否被污染并重签重建
对外通报按监管与合同义务评估披露(含CRA/GB/T 43698-2024场景下的供应链通报要求)

03 · 自托管Runner风险基线

  • 拒绝共享持久化Runner执行不可信代码:处理fork PR的job应跑在一次性(ephemeral)Runner上,任务结束即销毁——否则恶意PR可留下持久化后门并污染后续构建(与第4页L3临时性基线同源);
  • 网络出口收敛:Runner默认放通互联网是高危配置,按构建需求白名单化出口;防止构建脚本外联C2或回传源码;
  • 凭证作用域最小化:自托管Runner上 Secrets按job注入、不落盘;Runner主机禁装无关软件、纳入主机EDR覆盖;
  • 公共仓库自托管Runner视为高危:GitHub官方文档明确警告:公共仓库workflow不应在自托管Runner运行不可信PR代码——其所在网络与凭证可能被直接利用。

04 · Secrets管理与仓库侧防护

控制说明
集中式密钥库HashiCorp Vault、云厂商Secrets Manager等动态签发数据库/中间件凭证;流水线只获得句柄不接触明文
推送保护(Push Protection)GitHub Secret Scanning的推送保护在提交含已知模式密钥时直接阻断——将泄露消灭在入库前(2022年起逐范围开放)
日志遮蔽与审计CI平台自动遮蔽打印的Secrets;对遮蔽失败的运行告警(tj-actions事件的核心教训之一)
第三方App/集成审计GitHub Apps、Deploy Keys、OAuth授权定期盘点,移除僵尸集成(供应链事件常见初始入口)
包注册中心账户加固维护者强制2FA(PyPI关键项目2022年7月起强制)、发布令牌绑定IP/CI、启用sigstore签名发布(npm支持provenance发布证明)

05 · 流水线安全核查清单(摘要)

  • 云凭证全部从静态令牌迁移至OIDC联邦,角色信任策略校验分支/环境组合;
  • 第三方Action固定commit SHA;每月自动审计Action更新与异常变更;
  • pull_request_target类事件禁用执行来自fork的不可信代码;
  • 生产发布经Environment保护规则+人工评审;签名密钥仅存KMS;
  • 所有workflow输出经Secrets遮蔽校验;日志读取权限最小化;
  • 自托管Runner一次性化、出口白名单、纳入主机防护。

本节参考来源(第7页)

[1]

GitHub Actions OIDC工作负载身份官方文档(2021年10月功能上线):docs.github.com。

[2]

Cider Security《Poisoned Pipeline Execution (PPE)》研究(2022年,团队后并入Palo Alto Networks,成果由Legit Security延续):owasp.org/www-project-top-10-ci-cd-security-risks(PPE已收录为CICD-SEC-4)、paloaltonetworks.com/cyberpedia。

[3]

CVE-2025-30066(tj-actions/changed-files)与CVE-2025-30154(reviewdog/action-setup)NVD条目:nvd.nist.gov;CISA KEV收录记录:cisa.gov/kev。

[4]

Step Security对该事件的分析博客(2025年3月):stepsecurity.io/blog(tj-actions事件分析专文)。

[5]

GitHub自托管Runner安全官方警告:docs.github.com。

[6]

GitHub Secret Scanning与Push Protection文档:docs.github.com。

[7]

Codecov事件官方披露(2021年4月):about.codecov.io/security-update;PyPI 2FA政策公告(2022年):blog.pypi.org。