企业级指南:docker-compose.yml 语法怎么写?如何确定参数?
对于刚接触容器编排的开发和运维人员来说,面对 docker-compose.yml 常常无从下手:“我怎么知道这里该写什么参数?这些缩进和键值对的规则到底是什么?”
实际上,编写 Compose 文件的核心在于“翻译思维”和“骨架思维”。本文将为你拆解 docker-compose.yml 的结构逻辑、参数推导方法、核心语法规则以及官方权威参考渠道。
一、 核心思维 1:三大核心骨架(骨架思维)
任何一个 docker-compose.yml 文件,无论多复杂,其最顶层只有四大类目。你可以把它们想象成盖房子的骨架:
version: '3.8' # 1. 声明语法版本(现代 Compose 规范中此项已变为可选,但推荐保留)
services: # 2. 【核心】定义有哪些容器服务(比如 web、mysql、redis 等)
web-service:
image: nginx:alpine
networks: # 3. 【可选】定义隔离的网络命名空间(如不写,Compose 会默认创建一个)
prod-net:
volumes: # 4. 【可选】定义需要持久化的命名数据卷
db-data:
二、 核心思维 2:从 docker run 翻译到 Compose(翻译思维)
“我怎么知道里面应该填哪些参数?” —— 答案是:所有的 Compose 参数,都是从普通的 docker run 命令参数 1:1 翻译过来的。
只要你会写 docker run,你就会写 docker-compose.yml。请参考以下映射表:
docker run 命令行参数 |
对应的 docker-compose.yml 键名 |
语法格式示例 |
|---|---|---|
--name my-nginx |
container_name |
container_name: my-nginx |
-p 8080:80 |
ports |
ports: - "8080:80" |
-v /host:/container |
volumes |
volumes: - /host:/container |
-e ENV_VAR=prod |
environment |
environment: - ENV_VAR=prod |
--network my-net |
networks |
networks: - my-net |
--restart unless-stopped |
restart |
restart: unless-stopped |
--cpus="1.5" |
deploy.resources.limits.cpus |
deploy: resources: limits: cpus: '1.5' |
翻译演练:
- 原始命令:
docker run -d --name my-web -p 8080:80 -v /data:/usr/share/nginx/html --restart unless-stopped nginx:alpine - 翻译为
docker-compose.yml:version: '3.8' services: my-web-service: # 服务的自定义逻辑名 image: nginx:alpine # 基础镜像 container_name: my-web # 容器名 (--name) ports: - "8080:80" # 端口映射 (-p) volumes: - /data:/usr/share/nginx/html # 挂载目录 (-v) restart: unless-stopped # 重启策略 (--restart)
三、 高频核心参数语法规则
1. 端口映射 (ports)
- 规则:建议永远用双引号括起来。
- 为什么:YAML 语言会将形如
22:22或80:80的未加引号数字误解析为“六十进制”的时间(比如将 22:22 解析为 1342 分钟),从而导致端口映射错误。 - 正确写法:
ports: - "8080:80" - "127.0.0.1:3306:3306" # 仅允许本地回环访问
2. 环境配置 (environment)
支持两种写法,企业推荐使用列表(Array)写法:
- 写法 A(列表格式,推荐):使用
-和=。environment: - SPRING_PROFILES_ACTIVE=prod - DB_HOST=mysql-server - 写法 B(字典格式):使用冒号
:。
注:若环境变量的值本身包含冒号,写法 B 极易引发 YAML 解析错误,因此推荐写法 A。environment: SPRING_PROFILES_ACTIVE: prod DB_HOST: mysql-server
3. 数据卷挂载 (volumes)
分为 绑定挂载(Bind Mount) 和 命名卷挂载(Named Volume):
services:
web:
image: nginx
volumes:
- /opt/nginx/html:/usr/share/nginx/html:ro # 1. 绑定挂载(宿主机路径:容器路径:只读)
- mysql-data:/var/lib/mysql # 2. 命名卷挂载(数据卷名:容器路径)
volumes:
mysql-data: # 凡是使用了命名卷,必须在顶层 volumes 下声明该卷名
四、 编写配置规则去哪里看?
在实际编写时,遇到不确定的参数,有以下三个最权威的查阅渠道:
1. 官方规范文档(最权威的参数字典)
Docker 官方已经将原有的 V2、V3 语法合并统一为 Compose Specification(Compose 规范)。
- 查阅地址:Compose file reference (Docker Docs)
- 使用方法:在这个页面,左侧导航栏列出了所有合法的根元素。点击
services,可以展开查阅其下属的build、deploy、environment、ports等每一个子参数的详细语法和示例。
2. 利用 IDE 自动补全与 Schema 校验(效率最高、最防错)
在编写 YAML 时,强烈建议使用现代编辑器(如 VS Code)并安装 Docker 官方插件:
- 在 VS Code 中搜索并安装插件:
Docker(由 Microsoft 提供)。 - 新建一个名为
docker-compose.yml的文件。 - 输入双引号、冒号或按
Ctrl + Space(空格键),编辑器会基于官方的 JSON Schema 弹出合法的参数提示。 - 将鼠标悬停在某个参数(如
depends_on)上,编辑器会直接弹出该参数的官方英文解释和数据类型要求。
五、 企业级标准:带有详细逐行注释的实战案例
以下是一份可以直接作为企业 Wiki 规范和起步模板的配置文件,展示了多服务协作的编写规范:
# 声明 Compose 语法版本(3.8 是目前单机编排最成熟、兼容性最好的版本)
version: '3.8'
# 1. 定义全局共享的隔离网络
networks:
app-net:
driver: bridge # 驱动为本地桥接网络
# 2. 定义全局持久化命名卷
volumes:
db-store:
driver: local # 存储在本地
# 3. 定义容器服务集
services:
# -------------------- 数据库服务 --------------------
database-server:
image: mysql:8.0 # 1. 指定镜像及 Tag
container_name: prod-mysql # 2. 定义容器名
networks:
- app-net # 3. 将容器加入定义好的隔离网络
volumes:
- db-store:/var/lib/mysql:rw # 4. 持久化数据到命名卷,读写模式
environment:
- MYSQL_ROOT_PASSWORD=My_DB_Pass_2024 # 5. 注入环境变量
- MYSQL_DATABASE=production_db
restart: unless-stopped # 6. 重启策略:非人工手动停止则总是自动重启
healthcheck: # 7. 定义健康检查,保证数据库就绪后才让后端连接
test: ["CMD", "mysqladmin", "ping", "-h", "localhost"]
interval: 10s # 检查间隔
timeout: 5s # 超时时间
retries: 3 # 失败重试次数
# -------------------- 后端业务服务 --------------------
web-api:
image: reg.enterprise.com/web/api:v1.0.0
container_name: prod-api-service
networks:
- app-net
environment:
- SPRING_PROFILES_ACTIVE=prod
- DB_HOST=database-server # 通过服务名直接连接数据库,无需写死 IP
deploy:
resources: # 8. 资源限制(防止单个容器消耗整机 CPU 和内存)
limits:
cpus: '1.5' # 限制最大使用 1.5 核 CPU
memory: 1G # 限制最大使用 1G 内存
depends_on: # 9. 拓扑依赖控制
database-server:
condition: service_healthy # 关键:必须等数据库“健康”后,本容器才开始启动
restart: unless-stopped
浙公网安备 33010602011771号