composer.lock 必须提交到 Git,它是保障多环境依赖一致性的唯一强约束,记录精确版本、哈希值和依赖树快照;忽略或未提交将导致 composer install 退化为按 composer.json 重新解析,引发版本错乱与运行时错误。

composer.lock 必须提交到 Git,不能忽略
只要 .gitignore 里写了 composer.lock,或者有人没 git add composer.lock,所有后续 composer install 就会退化成按 composer.json 重新解析——结果就是开发机装的是 topthink/think-swoole v3.1.4,测试机拉到 v3.2.0,后者要求 PHP 8.1+,直接报 ParseError: syntax error。
这不是“可能出问题”,是“一定出问题”。composer.lock 是多环境一致的唯一强保障,它记录了每个包的精确版本、哈希值、依赖树快照。没有它,composer install 就失去了“安装确定版本”这个核心能力。
- 检查当前项目是否已提交:
git ls-files | grep composer.lock - 如果输出为空,立刻执行:
git add composer.lock && git commit -m "chore: add composer.lock" - CI/CD 流水线中,部署前必须加一步:
ls -la composer.lock,缺失即失败
哪些文件该进 .gitignore?只留必要项
composer.json 和 composer.lock 必须在 Git 中;其余一律排除。常见误配是把整个 vendor/ 加进 .gitignore 却忘了确认 composer.lock 是否已提交——这等于只留了一张空支票。
标准 .gitignore 片段应为:
vendor/ composer.phar composer-*.lock !composer.lock
注意最后一行:感叹号显式取消忽略 composer.lock,防止被上级规则覆盖。
-
composer.phar是可执行文件,不应进仓库(用系统全局或 CI 下载) -
composer-*.lock是某些插件生成的临时锁文件,和主composer.lock冲突,必须排除 - 绝对不要写
composer.*这种模糊规则,会误杀composer.lock
团队协作时 lock 文件冲突怎么处理?
当多人同时运行 composer update,composer.lock 被重写后推送到远程,就会产生合并冲突。这不是代码逻辑冲突,而是二进制依赖图快照的不可合并性。
正确做法不是手动编辑 lock 文件,而是统一回退 + 重装:
- 发现冲突后,立刻
git checkout HEAD -- composer.lock撤销本地修改 - 所有人执行:
git pull && composer install - 若需升级依赖,由一人执行
composer update vendor/package-name,提交新composer.lock,其他人只跑install
CI 流水线里永远用 composer install --no-dev,绝不允许 update 命令出现——否则 lock 文件会被悄悄覆盖,一致性彻底失效。
上线部署前必须验证 lock 文件有效性
composer install 成功不代表依赖正确。真正要验证的是:lock 文件里的版本是否真能匹配 composer.json 的约束,且所有包在目标环境中可安装。
最简验证方式:
- 本地执行:
composer install --dry-run,看是否报错Your lock file does not contain a compatible set of packages - 在目标环境(如 Docker 构建阶段)运行:
composer show | head -n 5,对比关键包(如thinkphp/framework)的 patch 版本号是否与本地一致 - CI 中加一行:
diff -q composer.lock origin/main:composer.lock || echo "LOCK FILE OUT OF SYNC"
很多人以为提交了 lock 文件就万事大吉,但没验证它是否被意外篡改过,或是否与 composer.json 实际内容脱节——这才是线上故障最隐蔽的源头。











