根本原因是直连 packagist.org 超时且镜像源未生效;应通过 -vvv 日志确认真实请求地址,确保使用阿里云等国内镜像源,并在 alpine 镜像中预先安装 ca-certificates 证书。

为什么 RUN composer install 总卡在 “Resolving packages…”
这不是 Composer 慢,是它在等 packagist.org 响应,而国内直连基本超时。即使你设了镜像源,也可能被其他配置覆盖或没生效。
- 用
composer install --no-interaction -vvv 2>&1 | grep "Downloading"查真实请求地址,确认是否走阿里云源(如https://mirrors.aliyun.com/composer/) - 别用
COMPOSER_REPO_PACKAGIST环境变量替代composer config -g—— 它只影响当前命令,不持久化,后续composer require仍可能回退到默认源 - Alpine 镜像必须先装证书:
RUN apk add --no-cache ca-certificates,否则报SSL certificate problem中断安装
Dockerfile 中 COPY 和 RUN 的顺序怎么写才不重装 vendor
顺序错一丁点,Docker 层缓存就失效,每次改代码都重装全部依赖。
- 必须先
COPY composer.json composer.lock ./,再RUN composer install --no-dev --optimize-autoloader --classmap-authoritative - 绝对不要在
RUN composer install前COPY . /app—— 这会让任何源码改动污染依赖层 -
composer.lock不能被.dockerignore排除,否则构建时找不到它,composer install会退化成update,破坏可重现性 - vendor 目录不用
COPY,靠层缓存自动复用;但要确保composer.lock内容稳定(比如 Git 提交前不手动改时间戳)
多阶段构建里 vendor 怎么安全复制到运行镜像
vendor 不是“传过去”,而是通过构建阶段的输出层被 COPY --from=builder 显式提取。缓存 mount 和 vendor 复用是两件事,混用会出问题。
- 第一阶段(builder)用完整 PHP 镜像(如
php:8.2-cli),装齐扩展(zip、mbstring)、装 Composer、跑composer install - 第二阶段(runtime)用精简镜像(如
php:8.2-fpm-alpine),只COPY --from=builder /app/vendor /app/vendor,不带 Composer 或源码工具 - 如果 builder 阶段用了
--no-scripts,而 runtime 需要 autoload 类映射,得在第二阶段单独跑composer dump-autoload --classmap-authoritative(注意用户权限) - 两个阶段的 PHP 版本和发行版(Debian/Alpine)必须完全一致,否则
ext-zip或platform配置会出兼容性问题
BuildKit 缓存怎么配才真加速下载
BuildKit 的 --mount=type=cache 不是开关一开就生效,漏一个硬条件,缓存就白配。
- 启用 BuildKit:
DOCKER_BUILDKIT=1 docker build .或export DOCKER_BUILDKIT=1 - 必须写全:
RUN --mount=type=cache,id=composer,target=/root/.composer/cache composer install --no-dev - 查真实缓存路径:
composer config cache-dir,别假设是/root/.composer/cache—— 自定义镜像可能改过 - CI 环境中,不同 runner 若未共享 cache 存储后端(如
buildkitd的--oci-worker-gc配置),id=composer也起不了作用
composer.lock 没变,只要其中一项不匹配,vendor 就可能运行时报错或构建失败。











