生产环境必须用全局镜像,唯一可靠方式是执行composer config -g repo.packagist composer https://mirrors.aliyun.com/composer/,且需严格满足三要素:带-g参数、键名为repo.packagist(非复数)、url末尾带斜杠;同时composer install须加--no-dev --no-scripts --no-autoloader --prefer-dist四参数才真正稳定。

生产环境必须用全局镜像,且只认 composer config -g repo.packagist
CI/CD 或部署脚本里执行 composer install 却卡在 Loading composer repositories,八成是镜像没走成。生产环境不能依赖项目级配置——composer.json 里的 repositories 字段在 Docker 构建、root 用户部署、多用户 CI runner 场景下极易被忽略或覆盖。
唯一可靠方式是全局写死:composer config -g repo.packagist composer https://mirrors.aliyun.com/composer/。
注意三点:
- 必须带 -g,否则只改当前目录的 composer.json
- 键名是 repo.packagist(不是 repos.packagist,多一个 s 就静默失效)
- URL 末尾斜杠不能少,https://mirrors.aliyun.com/composer/ ✅,https://mirrors.aliyun.com/composer ❌(会拼出 /p2// 导致 404)
composer install 必须加这四个参数才算真稳定
光换镜像源只是第一步。生产环境 composer install 不加参数,等于裸奔:
- --no-dev:跳过 require-dev,避免拉 phpunit 等大体积包,也防意外执行测试工具脚本
- --no-scripts:禁用 post-install-cmd 类脚本,ThinkPHP 的 clear:runtime、Laravel 的 optimize 在只读文件系统或并发部署时必挂
- --no-autoloader:先不生成 autoload,避免因权限或路径问题中断整个流程
- --prefer-dist:强制走 ZIP 包而非 git clone,减少网络和 I/O 不确定性
装完再单独跑 composer dump-autoload -o,可控、可重试、可捕获错误。
验证镜像是否真生效?别信日志,看 composer config -g repo.packagist
运行 composer install -vvv 看到 mirrors.aliyun.com 请求日志,不代表镜像已生效——那只是缓存残留或 fallback 行为。
真正判断依据只有一条:composer config -g repo.packagist 输出必须是完整 JSON:{"type": "composer", "url": "https://mirrors.aliyun.com/composer/"}
如果返回空、null、报错,或者输出里是 packagist.org,说明配置根本没写进去。
CI 脚本开头务必加这一句做断言,别等构建失败才查。
Docker 构建中容易漏掉的两个硬性检查点
很多线上部署失败,不是镜像配错了,而是构建上下文本身不完整:
- .dockerignore 里不能忽略 composer.lock,否则 composer install 实际退化为 update,版本不可控
- COPY 后必须确认 ls -l 输出里有 composer.lock 和 composer.json,缺一不可
另外,某些 CI 镜像(如 GitHub Actions 默认 ubuntu-latest)自带旧版 Composer 配置,即使你本地配好了,流水线里仍走官方源。解决方案:在 steps 开头显式执行一次 composer config -g repo.packagist composer https://mirrors.aliyun.com/composer/,覆盖掉默认配置。











