☰
第 7 章:Docker Compose 多容器编排
2026/10/12 2:25:25 网站建设 项目流程

前几章已经学会了单个容器的运行和镜像构建,但真实项目很少只有一个容器:后端、数据库、缓存、网关、消息队列通常要一起工作。Docker Compose 就是用来解决这个问题的:用一份docker-compose.yml声明所有服务,然后一条命令启动、停止、查看、重建。

注意:现在推荐使用Compose V2,命令是docker compose,中间是空格;旧版docker-compose已经停止维护。


7.1 为什么需要 Docker Compose

如果不用 Compose,启动一个“应用 + MySQL + Redis”至少要执行三条docker run,还要手动创建网络、管理数据卷、处理依赖顺序:

1docker network create app-net 2docker run -d --name mysql --network app-net -e MYSQL_ROOT_PASSWORD=123456 mysql:8.0 3docker run -d --name redis --network app-net redis:7-alpine 4docker run -d --name app --network app-net -p 8080:8080 myapp:1.0

换成 Compose 后,只需要一个文件、一条命令:

1docker compose up -d

Compose 主要解决:

  • 多容器一键启停
  • 服务间网络通信自动配置
  • 数据卷统一管理
  • 环境配置可版本化、可复制
  • 开发、测试、生产环境统一编排方式

7.2 docker-compose.yml 文件结构

Compose 文件默认放在项目根目录,文件名是docker-compose.yml或compose.yaml。

1services: # 必选:定义所有服务,每个服务对应一个容器 2 web: 3 image: nginx:alpine 4 db: 5 image: mysql:8.0 6 7volumes: # 可选:声明命名数据卷,用于持久化 8 db_data: 9 10networks: # 可选:自定义网络 11 app_net: 12 driver: bridge

说明:从 Compose Specification 起,version字段已经不再推荐必须写;如果为了兼容旧文档,可以保留version: "3.8"。


7.3 services 核心配置项

每个服务对应一个容器,下面是最常用的字段。

7.3.1 image / build
1services: 2 web: 3 image: nginx:alpine 4 # 直接使用已有镜像 5 6 api: 7 build: ./api 8 # 根据 ./api 目录下的 Dockerfile 构建镜像 9 10 api2: 11 build: 12 context: ./api 13 dockerfile: Dockerfile.prod 14 args: 15 APP_ENV: production 16 # 更精细地指定构建上下文、Dockerfile 名称和构建参数

场景:数据库、缓存、网关通常用image;自己的业务代码通常用build。

7.3.2 container_name
1services: 2 web: 3 image: nginx:alpine 4 container_name: my-nginx

说明:container_name会固定容器名称,方便排查;但指定后无法使用--scale扩容,因为多个同名容器会冲突。

7.3.3 ports
1services: 2 web: 3 image: nginx:alpine 4 ports: 5 - "8080:80" 6 # 宿主机 8080 -> 容器 80 7 8 - "127.0.0.1:3000:3000" 9 # 只绑定本机地址,更安全 10 11 - "5000" 12 # 只暴露容器端口,宿主机端口随机分配

建议:数据库、缓存这类服务通常不需要暴露到宿主机,只在容器网络内部访问即可。

7.3.4 volumes
1services: 2 db: 3 image: mysql:8.0 4 volumes: 5 - db_data:/var/lib/mysql 6 # 命名卷:适合数据库持久化 7 8 web: 9 image: nginx:alpine 10 volumes: 11 - ./html:/usr/share/nginx/html 12 # 绑定挂载:适合开发时同步代码

顶层声明命名卷:

1volumes: 2 db_data:

说明:数据库、Redis、消息队列等状态服务必须使用命名卷;开发调试时可以用绑定挂载实现代码热更新。

7.3.5 environment / env_file
1services: 2 db: 3 image: mysql:8.0 4 environment: 5 MYSQL_ROOT_PASSWORD: "123456" 6 MYSQL_DATABASE: mydb 7 TZ: Asia/Shanghai 8 # 直接写在 YAML 中 9 10 api: 11 image: myapp:latest 12 env_file: 13 - .env 14 - .env.local 15 # 从文件加载环境变量,更适合管理敏感信息

.env文件示例:

1DB_HOST=db 2DB_PORT=3306 3DB_USER=root 4DB_PASSWORD=123456

建议:密码、密钥不要直接写进docker-compose.yml,优先使用env_file,并把.env加入.gitignore。

7.3.6 depends_on
1services: 2 api: 3 image: myapp:latest 4 depends_on: 5 - db 6 - redis 7 # 先启动 db 和 redis,再启动 api 8 9 db: 10 image: mysql:8.0 11 healthcheck: 12 test: ["CMD", "mysqladmin", "ping", "-h", "localhost"] 13 interval: 5s 14 timeout: 3s 15 retries: 10 16 start_period: 30s 17 18 api2: 19 image: myapp:latest 20 depends_on: 21 db: 22 condition: service_healthy 23 redis: 24 condition: service_started 25 # 等待 db 健康检查通过后再启动 api2

重要:depends_on默认只保证启动顺序,不保证服务已经就绪。数据库容器启动了,不代表 MySQL 已经完成初始化。生产环境建议配合healthcheck使用。

7.3.7 restart
1services: 2 web: 3 image: nginx:alpine 4 restart: unless-stopped 5 # 除非手动停止,否则自动重启 6 7 api: 8 image: myapp:latest 9 restart: on-failure 10 # 只有异常退出时才重启

可选值:

值含义适用场景
no不自动重启一次性任务
always总是重启长期运行服务
on-failure异常退出时重启需要区分正常退出
unless-stopped除非手动停止,否则重启生产环境常用
7.3.8 command / entrypoint
1services: 2 redis: 3 image: redis:7-alpine 4 command: redis-server --requirepass mypassword --appendonly yes 5 # 覆盖容器默认启动命令 6 7 api: 8 image: myapp:latest 9 entrypoint: ["python", "app.py"] 10 command: ["--port", "8080"]

场景:官方镜像默认启动命令不满足需求时,用command覆盖;需要固定入口程序时用entrypoint。

7.3.9 healthcheck
1services: 2 db: 3 image: mysql:8.0 4 healthcheck: 5 test: ["CMD", "mysqladmin", "ping", "-h", "localhost"] 6 interval: 10s 7 timeout: 5s 8 retries: 5 9 start_period: 30s

说明:健康检查可以配合depends_on使用,也可以让运维人员通过docker compose ps直观看到服务是否健康。

7.3.10 资源限制

普通 Compose 环境下推荐直接使用顶层字段:

1services: 2 api: 3 image: myapp:latest 4 cpus: 0.5 5 mem_limit: 512m 6 mem_reservation: 256m

说明:deploy.resources主要在 Swarm 模式下生效;普通docker compose up环境用cpus、mem_limit更可靠。


7.4 networks 网络配置

Compose 会自动为项目创建一个默认网络,所有服务默认加入该网络,并且可以通过服务名互相访问。

1services: 2 web: 3 image: nginx:alpine 4 networks: 5 - frontend 6 - backend 7 8 api: 9 image: myapp:latest 10 networks: 11 - backend 12 13 db: 14 image: mysql:8.0 15 networks: 16 - backend 17 18networks: 19 frontend: 20 driver: bridge 21 backend: 22 driver: bridge 23 internal: true 24 # internal: true 表示该网络不能访问外网,适合数据库层

场景:把网关、前端放在frontend网络,把后端、数据库、缓存放在backend网络,可以提升安全性。


7.5 volumes 数据卷配置

1services: 2 db: 3 image: mysql:8.0 4 volumes: 5 - db_data:/var/lib/mysql 6 7 redis: 8 image: redis:7-alpine 9 volumes: 10 - redis_data:/data 11 12 web: 13 image: nginx:alpine 14 volumes: 15 - ./html:/usr/share/nginx/html 16 17volumes: 18 db_data: 19 redis_data:

说明:命名卷由 Docker 管理,适合数据库;绑定挂载适合开发时同步代码。删除容器时,命名卷不会自动删除,避免误删数据。


7.6 常用命令

所有命令应在docker-compose.yml所在目录执行。

1docker compose version 2# 查看 Compose 版本 3 4docker compose config 5# 校验配置文件是否合法,并输出解析后的完整配置 6 7docker compose up 8# 前台启动所有服务,适合调试 9 10docker compose up -d 11# 后台启动所有服务,生产/日常最常用 12 13docker compose up -d --build 14# 重新构建镜像后再启动,适合修改 Dockerfile 后使用 15 16docker compose up -d --force-recreate 17# 强制重新创建容器 18 19docker compose ps 20# 查看当前项目所有容器状态 21 22docker compose logs 23# 查看所有服务日志 24 25docker compose logs -f 26# 实时滚动查看所有服务日志 27 28docker compose logs -f api 29# 只看 api 服务的日志 30 31docker compose logs --tail=100 -f api 32# 只看最近 100 行日志并持续跟踪 33 34docker compose stop 35# 停止所有容器,但不删除 36 37docker compose start 38# 启动已停止的容器 39 40docker compose restart 41# 重启所有容器 42 43docker compose restart api 44# 只重启 api 服务 45 46docker compose down 47# 停止并删除容器、网络,默认保留数据卷 48 49docker compose down -v 50# 停止并删除容器、网络和数据卷,慎用 51 52docker compose down --rmi all 53# 同时删除相关镜像 54 55docker compose exec api bash 56# 进入 api 容器终端 57 58docker compose exec db mysql -uroot -p 59# 进入 MySQL 命令行 60 61docker compose run --rm api python manage.py migrate 62# 运行一次性任务,执行后自动删除容器 63 64docker compose build 65# 构建所有需要构建的服务镜像 66 67docker compose build api 68# 只构建 api 服务镜像 69 70docker compose pull 71# 拉取所有服务依赖的最新镜像 72 73docker compose images 74# 查看服务使用的镜像 75 76docker compose top 77# 查看容器内运行的进程 78 79docker compose port api 8080 80# 查看 api 服务 8080 端口映射到宿主机的端口

7.7 实战一:Python Flask + MySQL + Redis

项目结构:

1flask-project/ 2├── app/ 3│ ├── app.py 4│ ├── requirements.txt 5│ └── Dockerfile 6├── docker-compose.yml 7└── .env

app/Dockerfile:

1FROM python:3.12-slim 2 3WORKDIR /app 4 5COPY requirements.txt . 6RUN pip install --no-cache-dir -r requirements.txt 7 8COPY . . 9 10RUN useradd -m appuser 11USER appuser 12 13EXPOSE 5000 14 15CMD ["gunicorn", "--bind", "0.0.0.0:5000", "app:app"]

docker-compose.yml:

1services: 2 api: 3 build: ./app 4 ports: 5 - "8000:5000" 6 environment: 7 - DB_HOST=db 8 - DB_PORT=3306 9 - DB_USER=root 10 - DB_PASSWORD=${DB_PASSWORD} 11 - DB_NAME=mydb 12 - REDIS_HOST=redis 13 - REDIS_PORT=6379 14 - TZ=Asia/Shanghai 15 env_file: 16 - .env 17 depends_on: 18 db: 19 condition: service_healthy 20 redis: 21 condition: service_started 22 restart: unless-stopped 23 volumes: 24 - ./app:/app 25 - /app/__pycache__ 26 networks: 27 - app_net 28 29 db: 30 image: mysql:8.0 31 environment: 32 MYSQL_ROOT_PASSWORD: ${DB_PASSWORD} 33 MYSQL_DATABASE: mydb 34 TZ: Asia/Shanghai 35 volumes: 36 - db_data:/var/lib/mysql 37 healthcheck: 38 test: ["CMD", "mysqladmin", "ping", "-h", "localhost"] 39 interval: 5s 40 timeout: 3s 41 retries: 10 42 start_period: 30s 43 restart: unless-stopped 44 networks: 45 - app_net 46 47 redis: 48 image: redis:7-alpine 49 command: redis-server --appendonly yes 50 volumes: 51 - redis_data:/data 52 restart: unless-stopped 53 networks: 54 - app_net 55 56volumes: 57 db_data: 58 redis_data: 59 60networks: 61 app_net: 62 driver: bridge

.env:

1DB_PASSWORD=StrongPass123

启动:

1docker compose up -d 2# 一键启动 Flask + MySQL + Redis 3 4docker compose logs -f api 5# 查看应用日志 6 7docker compose exec db mysql -uroot -pStrongPass123 8# 进入数据库

说明:volumes: - ./app:/app让开发时代码修改后容器内自动生效;- /app/__pycache__排除 Python 缓存目录,避免宿主机和容器缓存冲突。


7.8 实战二:Node.js + PostgreSQL + Redis

项目结构:

1node-project/ 2├── app/ 3│ ├── src/ 4│ ├── package.json 5│ ├── package-lock.json 6│ └── Dockerfile 7├── docker-compose.yml 8└── .env

app/Dockerfile:

1FROM node:20-alpine 2 3WORKDIR /app 4 5COPY package.json package-lock.json ./ 6RUN npm ci --only=production 7 8COPY src/ ./src/ 9 10RUN addgroup -S appgroup && adduser -S appuser -G appgroup 11USER appuser 12 13EXPOSE 3000 14 15CMD ["node", "src/index.js"]

docker-compose.yml:

1services: 2 web: 3 build: ./app 4 ports: 5 - "3000:3000" 6 environment: 7 - NODE_ENV=production 8 - DB_HOST=db 9 - DB_PORT=5432 10 - DB_USER=postgres 11 - DB_PASSWORD=${DB_PASSWORD} 12 - DB_NAME=mydb 13 - REDIS_HOST=redis 14 env_file: 15 - .env 16 depends_on: 17 db: 18 condition: service_healthy 19 redis: 20 condition: service_started 21 restart: unless-stopped 22 networks: 23 - node_net 24 25 db: 26 image: postgres:16-alpine 27 environment: 28 POSTGRES_PASSWORD: ${DB_PASSWORD} 29 POSTGRES_DB: mydb 30 volumes: 31 - pg_data:/var/lib/postgresql/data 32 healthcheck: 33 test: ["CMD-SHELL", "pg_isready -U postgres"] 34 interval: 5s 35 timeout: 3s 36 retries: 10 37 start_period: 20s 38 restart: unless-stopped 39 networks: 40 - node_net 41 42 redis: 43 image: redis:7-alpine 44 command: redis-server --requirepass ${REDIS_PASSWORD} --appendonly yes 45 volumes: 46 - redis_data:/data 47 restart: unless-stopped 48 networks: 49 - node_net 50 51volumes: 52 pg_data: 53 redis_data: 54 55networks: 56 node_net: 57 driver: bridge

7.9 实战三:Go + MySQL 多阶段构建

项目结构:

1go-project/ 2├── main.go 3├── go.mod 4├── go.sum 5├── Dockerfile 6├── docker-compose.yml 7└── .env

Dockerfile:

1FROM golang:1.22-alpine AS builder 2 3WORKDIR /app 4COPY go.mod go.sum ./ 5RUN go mod download 6COPY . . 7RUN CGO_ENABLED=0 GOOS=linux go build -ldflags="-s -w" -o myapp . 8 9FROM alpine:3.19 10 11WORKDIR /app 12COPY --from=builder /app/myapp . 13 14EXPOSE 8080 15CMD ["./myapp"]

docker-compose.yml:

1services: 2 app: 3 build: . 4 ports: 5 - "8080:8080" 6 environment: 7 - DB_HOST=mysql 8 - DB_PORT=3306 9 - DB_USER=root 10 - DB_PASSWORD=${DB_PASSWORD} 11 - DB_NAME=mydb 12 env_file: 13 - .env 14 depends_on: 15 mysql: 16 condition: service_healthy 17 restart: unless-stopped 18 networks: 19 - go_net 20 21 mysql: 22 image: mysql:8.0 23 environment: 24 MYSQL_ROOT_PASSWORD: ${DB_PASSWORD} 25 MYSQL_DATABASE: mydb 26 volumes: 27 - mysql_data:/var/lib/mysql 28 healthcheck: 29 test: ["CMD", "mysqladmin", "ping", "-h", "localhost"] 30 interval: 5s 31 timeout: 3s 32 retries: 10 33 start_period: 30s 34 restart: unless-stopped 35 networks: 36 - go_net 37 38volumes: 39 mysql_data: 40 41networks: 42 go_net: 43 driver: bridge

7.10 实战四:Nginx 反向代理 + 前后端分离

项目结构:

1fullstack/ 2├── frontend/ 3│ ├── dist/ 4│ └── Dockerfile 5├── backend/ 6│ ├── app.py 7│ ├── requirements.txt 8│ └── Dockerfile 9├── nginx/ 10│ └── default.conf 11└── docker-compose.yml

nginx/default.conf:

1server { 2 listen 80; 3 4 location / { 5 proxy_pass http://frontend:80; 6 } 7 8 location /api/ { 9 proxy_pass http://backend:5000; 10 } 11}

docker-compose.yml:

1services: 2 nginx: 3 image: nginx:1.27-alpine 4 ports: 5 - "80:80" 6 volumes: 7 - ./nginx/default.conf:/etc/nginx/conf.d/default.conf:ro 8 depends_on: 9 - frontend 10 - backend 11 restart: unless-stopped 12 networks: 13 - fullstack_net 14 15 frontend: 16 build: ./frontend 17 restart: unless-stopped 18 networks: 19 - fullstack_net 20 21 backend: 22 build: ./backend 23 environment: 24 - TZ=Asia/Shanghai 25 restart: unless-stopped 26 networks: 27 - fullstack_net 28 29networks: 30 fullstack_net: 31 driver: bridge

说明:只有 Nginx 暴露端口,前端和后端都在内部网络中,外部无法直接访问后端服务,这是一种常见的安全部署方式。

7.11 多环境配置

真实项目通常不会只有一份 Compose 配置。开发环境要方便调试,测试环境要接近生产,生产环境要稳定、安全、可观测。Compose 支持多文件合并,可以把公共配置和差异配置拆开。

7.11.1 多文件合并规则

Compose 默认会读取:

1docker-compose.yml 2docker-compose.override.yml

执行docker compose up时,后面的文件会覆盖前面的文件。

也可以显式指定:

1docker compose -f docker-compose.yml -f docker-compose.dev.yml up -d

合并规则:

  • 同名服务会被合并
  • 简单字段如image、command会被覆盖
  • 列表字段如ports、volumes、environment会追加
  • 后面的文件优先级更高

7.11.2 通用基础配置

docker-compose.yml放所有环境共用的部分:

1services: 2 api: 3 build: ./api 4 depends_on: 5 db: 6 condition: service_healthy 7 redis: 8 condition: service_started 9 restart: unless-stopped 10 networks: 11 - app_net 12 13 db: 14 image: mysql:8.0 15 environment: 16 MYSQL_ROOT_PASSWORD: ${DB_PASSWORD} 17 MYSQL_DATABASE: mydb 18 volumes: 19 - db_data:/var/lib/mysql 20 healthcheck: 21 test: ["CMD", "mysqladmin", "ping", "-h", "localhost"] 22 interval: 5s 23 timeout: 3s 24 retries: 10 25 start_period: 30s 26 restart: unless-stopped 27 networks: 28 - app_net 29 30 redis: 31 image: redis:7-alpine 32 volumes: 33 - redis_data:/data 34 restart: unless-stopped 35 networks: 36 - app_net 37 38volumes: 39 db_data: 40 redis_data: 41 42networks: 43 app_net: 44 driver: bridge

7.11.3 开发环境配置

docker-compose.dev.yml侧重调试体验:

1services: 2 api: 3 ports: 4 - "8080:8080" 5 environment: 6 - APP_ENV=development 7 - DEBUG=true 8 volumes: 9 - ./api:/app 10 - /app/node_modules 11 command: ["npm", "run", "dev"] 12 13 db: 14 ports: 15 - "3306:3306" 16 environment: 17 - MYSQL_ROOT_PASSWORD=dev123456 18 19 redis: 20 ports: 21 - "6379:6379"

启动开发环境:

1docker compose -f docker-compose.yml -f docker-compose.dev.yml up -d

场景:开发时通过绑定挂载同步代码,数据库和 Redis 暴露端口方便本地客户端连接。

7.11.4 测试环境配置

docker-compose.test.yml通常用于 CI 或本地集成测试:

1services: 2 api: 3 environment: 4 - APP_ENV=test 5 - DB_HOST=db 6 - REDIS_HOST=redis 7 command: ["npm", "run", "test"] 8 9 db: 10 environment: 11 MYSQL_ROOT_PASSWORD: test123 12 MYSQL_DATABASE: mydb_test

运行测试:

1docker compose -f docker-compose.yml -f docker-compose.test.yml up --abort-on-container-exit

说明:--abort-on-container-exit表示任意容器退出后自动停止整个编排,适合测试任务。

7.11.5 生产环境配置

docker-compose.prod.yml侧重稳定和安全:

1services: 2 api: 3 image: myapp:1.2.0 4 environment: 5 - APP_ENV=production 6 - DEBUG=false 7 ports: 8 - "127.0.0.1:8080:8080" 9 cpus: 1 10 mem_limit: 512m 11 logging: 12 driver: json-file 13 options: 14 max-size: "10m" 15 max-file: "3" 16 17 db: 18 ports: [] 19 environment: 20 MYSQL_ROOT_PASSWORD: ${DB_PASSWORD} 21 22 redis: 23 ports: [] 24 command: redis-server --requirepass ${REDIS_PASSWORD} --appendonly yes

启动生产环境:

1docker compose -f docker-compose.yml -f docker-compose.prod.yml up -d

建议:

  • 生产环境数据库、缓存不要暴露端口
  • 敏感信息通过.env注入
  • 配置日志轮转,避免磁盘占满
  • 使用固定镜像标签,不要用latest

7.11.6 使用 profile 控制可选服务

有些服务不是每个环境都需要,比如监控、文档、测试工具:

1services: 2 api: 3 image: myapp:1.0 4 5 docs: 6 image: swaggerapi/swagger-ui 7 ports: 8 - "8081:8080" 9 profiles: 10 - dev 11 - docs 12 13 prometheus: 14 image: prom/prometheus 15 profiles: 16 - monitoring

启动时选择 profile:

1docker compose --profile dev up -d 2docker compose --profile monitoring up -d

场景:开发时开启文档服务,生产时只启动核心业务和监控。

7.11.7 不同项目类型的多环境建议

项目类型开发重点生产重点
Web 后端代码热更新、调试端口、本地数据库固定镜像、日志轮转、资源限制
前后端分离前端 dev server、反向代理Nginx 静态资源 + API 代理
微服务多服务并行启动、独立日志健康检查、重启策略、网络隔离
数据服务挂载测试数据、快速重置命名卷持久化、备份策略
AI/推理服务GPU 设备映射、模型挂载资源限制、只读模型卷、低权限运行

7.12 常见问题排查

7.12.1 配置文件语法错误

1docker compose config

如果 YAML 缩进、字段名写错,这个命令会直接报错。建议每次修改后先执行一次校验。

7.12.2 容器启动后立即退出

查看日志:

1docker compose logs api 2docker compose logs --tail=200 api

常见原因:

  • 应用启动报错
  • 缺少环境变量
  • 数据库未就绪
  • 端口被占用
  • 启动命令写错

可以先前台启动观察输出:

1docker compose up api

7.12.3 服务之间无法访问

Compose 默认会为项目创建网络,服务之间可以通过服务名访问:

1docker compose exec api ping db 2docker compose exec api curl http://db:3306

如果自定义了网络,需要确认服务都加入了同一个网络:

1services: 2 api: 3 networks: 4 - app_net 5 6 db: 7 networks: 8 - app_net

7.12.4 端口冲突

如果宿主机端口已被占用,启动时会报错。可以修改映射端口:

1ports: 2 - "8081:80"

查看宿主机端口占用:

1ss -lntp | grep 8080

7.12.5 数据库连接失败

常见原因:

  • 应用连接地址写成了localhost
  • 数据库尚未初始化完成
  • 密码或数据库名不一致
  • 健康检查未通过

正确做法是把数据库地址写成服务名:

env

1DB_HOST=db 2DB_PORT=3306

并配合健康检查:

yaml

1depends_on: 2 db: 3 condition: service_healthy

7.12.6 数据卷数据丢失或残留

命名卷不会随docker compose down自动删除:

1docker compose down 2# 保留数据卷 3 4docker compose down -v 5# 删除数据卷,慎用

查看现有卷:

1docker volume ls 2docker volume inspect project_db_data

建议:数据库、Redis、消息队列等状态服务一定要使用命名卷;测试环境重置时再考虑使用-v。

7.12.7 镜像构建失败

重新构建:

1docker compose build --no-cache api 2docker compose up -d --build

如果构建很慢,可以检查:

  • COPY顺序是否合理
  • 是否把不必要的文件放进了构建上下文
  • 是否缺少.dockerignore

推荐.dockerignore:

1node_modules 2.git 3.env 4*.log 5dist

7.12.8 环境变量没有生效

检查方式:

1docker compose config 2docker compose exec api env

注意几点:

  • .env文件默认只在 Compose 文件所在目录生效
  • environment和env_file可以同时使用
  • ${VAR}会在 Compose 解析阶段替换
  • 容器内环境变量以最终合并结果为准

7.12.9 日志太多导致磁盘占满

给服务配置日志轮转:

1services: 2 api: 3 logging: 4 driver: json-file 5 options: 6 max-size: "10m" 7 max-file: "3"

查看日志占用:

1docker compose logs --tail=50 api

7.12.10 容器权限问题

如果应用需要写文件,但容器内用户权限不足,可以:

1services: 2 api: 3 user: "1000:1000" 4 volumes: 5 - ./data:/app/data

或者在 Dockerfile 中创建合适用户,避免直接使用root。

7.12.11 快速诊断命令汇总

bash

1docker compose config 2# 检查配置是否正确 3 4docker compose ps 5# 查看容器状态 6 7docker compose logs -f 8# 查看所有服务日志 9 10docker compose logs -f api 11# 查看单个服务日志 12 13docker compose exec api bash 14# 进入容器排查 15 16docker compose top 17# 查看容器内进程 18 19docker compose images 20# 查看使用的镜像 21 22docker compose port api 8080 23# 查看端口映射 24 25docker system df 26# 查看 Docker 磁盘占用 27 28docker volume ls 29# 查看数据卷

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询