composer 不校验 vendor 文件哈希,需手动比对 composer.lock 与 installed.json 结构一致性,并抽样验证 autoload_real.php 等高危文件哈希;ci 中推荐用排除干扰项的 tar 快照哈希比对。

Composer 不会在运行时自动校验 vendor/ 中已安装文件的哈希值,composer.lock 里的 dist.sha256 只在下载归档包(zip/tar)时用一次,装完就丢——所以 vendor 被篡改、注入恶意代码、CI 构建后被污染,它完全不感知。
怎么确认 vendor 文件和 lock 记录的哈希一致?
没有内置命令一键比对,但可快速验证关键路径是否“被动过”。核心思路是:只比对 vendor/composer/installed.json 和 composer.lock 的 packages 列表是否匹配,再抽样检查几个高风险入口文件的哈希。
- 先跑
composer show --locked --format=json | jq '.packages[] | select(.name == "composer/composer")' | jq -r '.dist.sha256'拿到某个包的预期哈希 - 进
vendor/composer/installed.json找同名包,看dist块里有没有shasum字段(注意:不是所有包都存这个,只有 dist 安装的才有) - 手动计算实际文件哈希:
sha256sum vendor/composer/autoload_real.php—— 这个文件被改了最危险,但 lock 里根本不记录它的哈希,只能靠经验盯住 - 更省事的做法:用
diff 看结构是否一致(忽略时间戳、dev 分支等浮动字段)
为什么 composer install 没报错,但 vendor/autoload.php 已被替换?
vendor/autoload.php 是个静态引导文件,内容固定为 require_once __DIR__ . '/composer/autoload_real.php';。Composer 安装时不校验它,dump-autoload 也不读它,改掉这行或插入 eval($_GET['x']),全程零警告。
围绕关键发现、作用机制、临床相关性及研究局限性展开讨论。适用于撰写或优化任何生物医学论文的“讨论(Discussion)”部分——包括结果解读、与既往文献关联、阐释意外发现、界定研究局限性,以及撰写结论。当用户输入以下任一指令时也会自动触发该功能: - “write my discussion” - “help me discuss my findings” - “how do I compare to prior studies” - “write the limitations par
- 它不参与任何哈希校验流程,lock 文件里压根没它的条目
- CI 构建后若允许写
vendor/目录,攻击者可直接覆盖该文件(比如通过未过滤的 log 写入或反序列化 gadget) - 生产环境必须设
vendor/为只读:chmod -R 555 vendor/(Linux)或用容器readonlyRootFilesystem: true - 检测脚本里应单独加一行:
[[ $(sha256sum vendor/autoload.php | cut -d' ' -f1) == "b0e4a7c9d8f1e2b3a4c5d6e7f8a9b0c1d2e3f4a5b6c7d8e9f0a1b2c3d4e5f6a7" ]] || echo "autoload.php tampered!"(哈希值按项目实际固化)
CI 中如何低成本做哈希快照比对?
全量下载+解压+目录哈希太重,CI 里推荐用 tar 快照法:把 clean install 后的 vendor/ 打包、算哈希,后续构建完立刻比对,排除非发布文件干扰。
- 首次生成快照:
tar --sort=name --owner=0 --group=0 --numeric-owner --mtime='UTC 2026-01-01' -cf vendor-snapshot.tar --exclude='./vendor/bin' --exclude='./vendor/composer/installed.json' vendor/ && sha256sum vendor-snapshot.tar > vendor-snapshot.sha256 - 每次构建后验证:
tar ... -cf vendor-current.tar ... && sha256sum -c vendor-snapshot.sha256 - 关键点:必须排除
vendor/bin/(含软链,跨平台哈希不稳)、installed.json(含安装时间戳)、.git/(不该进 vendor) - 别依赖
composer.lock的dist.sha256去校验解压后目录——它只对原始 zip 有效,且不同压缩工具、时间戳、文件顺序都会导致目录哈希变化
真正难防的不是哈希不匹配,而是你根本不知道该比对什么:lock 文件不记录 autoload.php,installed.json 不包含 dist 哈希,CI 快照容易漏排除项。动手前先想清楚,你要防的是供应链投毒,还是构建过程污染——目标不同,检查点和成本差很远。










