# Docker Compose v5 升级复盘:我是如何踩完所有兼容性坑的
版本跳跃带来的破坏性变更,往往比想象中更隐蔽。
背景:为什么我要升级
我在一个 2024 年搭建的 VPS 项目上继续开发,原来的 docker-compose.yml 使用的是 v2.40.2。某天我执行 docker compose version 时发现已经出到 v5.1.3(截至 2026-04-15),想着「小版本升级应该没问题」,结果触发了一系列连锁故障。
原始配置片段(来自 v2.40.2 项目):
version: "3.8"
services:
web:
build: .
ports:
- "80:80"
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost/"]
interval: 30s
timeout: 10s
retries: 3
这段配置在 v5.1.3 下出现了 3 个不同的错误。
第一个坑:build section 行为变更
**问题**:v5.0.0 移除了 internal buildkit builder,构建全部委托给 Docker Bake(与 docker build 命令一致)。原来 build.args 的语法仍然有效,但如果你的 docker-compose.yml 依赖了 docker build 内部的构建缓存(internal builder),配置会静默失效。
报错表现:
ERROR: compose file's build section uses unsupported features: internal builder is no longer supported
排查过程:
1. 确认报错来自 docker compose build
2. 检查 docker buildx version(需要 v0.30.0+,随 Docker Desktop 附带)
3. 查看 compose 文件是否使用了 build 的特定参数
解决方案:
# v5 兼容写法:显式使用 docker Bake
services:
web:
build:
context: .
dockerfile: Dockerfile
builder: default # 明确使用 external builder
如果不需要构建,直接用预编译镜像:
services:
web:
image: Nginx 性能调优:1.30-alpine
ports:
- "80:80"
第二个坑:healthcheck 的 CMD 写法
**问题**:v5 中 healthcheck 的 test 字段不再接受数组形式的 ["CMD", ...] 写法(虽然文档没明说,但实测 v5.1.3 会触发警告并建议改用字符串格式)。
报错表现:
WARNING: The test attribute must be a list or a string. Using list is deprecated.
排查过程:
1. 注释掉 healthcheck,看容器是否正常启动(是 → 问题在 healthcheck)
2. 逐字段移除测试,确认是 test 字段的问题
解决方案:
# 推荐写法(v5/v2 均兼容)
healthcheck:
test: "curl -f http://localhost/ || exit 1"
interval: 30s
timeout: 10s
retries: 3
start_period: 40s
# 如果镜像没有 curl,使用 wget 或直接 test HTTP 端口
healthcheck:
test: ["CMD", "wget", "-q", "--spider", "http://localhost/"]
interval: 30s
timeout: 10s
retries: 3
第三个坑:COMPOSE_COMPATIBILITY 变量被移除
**问题**:v5.0.1 恢复了 COMPOSE_COMPATIBILITY 支持(PR #13424),但仅限 v5.0.1+,如果你的 CI 环境还在用旧版 docker compose,这个变量在 v5 中行为已改变。
实测影响:
- 在 `COMPOSE_COMPATIBILITY=true` 环境下,v5 会降级部分行为,但 `version: "3.x"` 的 compose 文件在 v5 中会被视为「旧格式文件」,部分字段会被警告(不影响功能,但不推荐)。
**解决方案**:统一使用 version: "3.9" 或直接去掉 version 字段(v5 默认使用 Compose Specification,兼容度最高)。
# 推荐:去掉 version,使用 Compose Specification
services:
web:
image: nginx:1.30-alpine
第四个坑:端口绑定顺序
**问题**:v5 中 ports 的简短写法(如 "80:80")在某些网络模式下表现与 v2 不同。特别是在 network_mode: bridge 时,v5 会默认绑定到 0.0.0.0(所有接口),而 v2 某些版本只绑定到 127.0.0.1。
安全影响:如果你的服务不应该暴露到公网,这个变化会引发意外暴露。
排查命令:
# 查看容器实际监听的端口
docker inspect | grep -A 20 '"PortBindings"'
# 对比 v2 和 v5 的差异
docker run --rm nginx:1.30-alpine cat /etc/nginx/nginx.conf | grep listen
解决方案:
# 显式指定绑定 IP(v5/v2 兼容)
services:
web:
ports:
- "127.0.0.1:80:80" # 仅本地访问
升级检查清单
执行 docker compose version 确认是 v5.x 后,按以下顺序检查:
# 1. 检查 build 配置是否依赖 internal builder
docker compose config 2>&1 | grep -i "unsupported"
# 2. 检查 healthcheck 格式
docker compose config | grep -A 10 healthcheck
# 3. 检查端口绑定
docker compose ps
# 4. 如果使用了自定义网络,检查是否正常
docker network ls
docker network inspect _default
防坑建议
1. **不要跳过次版本号**:v2 → v5 的跳跃意味着你错过了 3 个中间版本的所有变更日志。升级前至少扫一遍 GitHub Changelog。
2. **CI 环境同步**:本地升级 docker compose 后,CI 环境的版本可能滞后。在 CI 的 Dockerfile 或 workflow 中明确指定版本:
- name: Install Docker Compose v5
# GitHub Actions 示例
run: |
curl -L "https://github.com/docker/compose/releases/download/v5.1.3/docker-compose-$(uname)-$(uname -m)" -o /usr/local/bin/docker-compose
chmod +x /usr/local/bin/docker-compose
3. 保留回滚能力:
# 备份当前配置
cp docker-compose.yml docker-compose.yml.backup
# 如果出问题,降级方法(Linux)
curl -L "https://github.com/docker/compose/releases/download/v2.40.2/docker-compose-$(uname)-$(uname -m)" -o /usr/local/bin/docker-compose
chmod +x /usr/local/bin/docker-compose
4. **使用 docker compose watch**:v5 引入了 watch 功能,可以在修改代码后自动重建容器,比手动 docker compose up --build 更方便。配置示例:
services:
web:
build: .
watch:
- action: rebuild
path: .
target: /app
我的升级时间线
| 时间 | 操作 | 结果 |
|---|---|---|
| 10:00 | 执行 `docker compose upgrade` | 提示已是最新版本(v2.40.2) |
| 10:05 | 手动下载 v5.1.3 二进制 | 安装成功 |
| 10:10 | `docker compose up -d` | build 报错 |
| 10:25 | 修复 build 配置 | 健康检查警告 |
| 10:40 | 修复 healthcheck | 端口暴露问题 |
| 11:00 | 全部修复完成 | 生产验证通过 |
整个过程花了约 1 小时。如果提前看 changelog,预计 15 分钟。
---
本文涉及版本(截至 2026-04-22,建议自行确认):
👉 立即参与 MiniMax:https://platform.minimaxi.com/subscribe/token-plan?code=E5yur9NOub&source=link
🔗 Related Tech Articles
Deep dive into related technical topics: