Skip to content

🎼 Docker Compose

为什么需要 Compose?

如果你的应用需要多个容器协作(比如 Web 应用 + 数据库 + 缓存),一个一个手动启动?太累了。Docker Compose 就是乐团指挥——用一个 YAML 文件定义所有服务,一条命令全部启动。

docker-compose.yml 基本语法

yaml
# docker-compose.yml(Compose V2 不再需要 version 字段)

services:
  # Web 应用服务
  web:
    build: .                          # 从当前目录构建
    ports:
      - "8080:3000"                   # 端口映射
    environment:
      - NODE_ENV=production
      - DB_HOST=db
      - REDIS_HOST=redis
    depends_on:
      - db
      - redis
    restart: unless-stopped

  # 数据库服务
  db:
    image: mysql:8.0
    environment:
      MYSQL_ROOT_PASSWORD: secret
      MYSQL_DATABASE: myapp
    volumes:
      - mysql-data:/var/lib/mysql
    restart: unless-stopped

  # 缓存服务
  redis:
    image: redis:7-alpine
    restart: unless-stopped

# 声明命名卷
volumes:
  mysql-data:

Compose 常用命令

bash
# 启动所有服务(后台运行)
docker compose up -d
[+] Running 4/4
 Network myproject_default    Created
 Container myproject-db-1     Started
 Container myproject-redis-1  Started
 Container myproject-web-1    Started

# 查看服务状态
docker compose ps
NAME                SERVICE    STATUS    PORTS
myproject-db-1      db         running   3306/tcp
myproject-redis-1   redis      running   6379/tcp
myproject-web-1     web        running   0.0.0.0:8080->3000/tcp

# 查看日志
docker compose logs -f web

# 停止所有服务
docker compose down

# 停止并删除卷(⚠️ 会丢失数据!)
docker compose down -v

# 重新构建并启动
docker compose up -d --build

# 只重启某个服务
docker compose restart web

# 扩展服务数量(启动 3 个 web 实例)
docker compose up -d --scale web=3

网络和卷配置

yaml
services:
  nginx:
    image: nginx
    networks:
      - frontend
      - backend
    ports:
      - "80:80"

  app:
    build: ./app
    networks:
      - backend
    volumes:
      - app-data:/app/data

  db:
    image: mysql:8.0
    networks:
      - backend
    volumes:
      - db-data:/var/lib/mysql

networks:
  frontend:     # 前端网络
  backend:      # 后端网络(隔离)

volumes:
  app-data:
  db-data:

💡 提示: 💡 网络隔离很重要!数据库只在backend网络,外部无法直接访问。只有 nginx 同时在两个网络中,能转发请求。