Docker Compose入门指南之一条命令启动多服务

 更新时间:2026年05月29日 08:43:27   作者:IT策士  
Docker Compose 的目标就是把这些步骤写进一个 YAML 文件,然后一条命令搞定一切,这篇就来带你入门 Compose,把 Flask + Redis 计数器应用的启动过程从"手动敲 8 条命令变成一条 docker compose up

在上一篇文章的末尾,我留了一个问题:每次启动 Flask + Redis 应用都要敲七八条命令,太累了。有没有更优雅的方式?

有。这就是我们今天的主角——Docker Compose

如果你跟着第 10 篇亲手敲过那几十条命令,一定能感受到手动管理的痛苦:要先创建网络、创建数据卷、启动 Redis、等待 Redis 就绪、启动 Flask……顺序不能错,参数不能漏,换一台机器又得重来一遍。Docker Compose 的目标就是把这些步骤写进一个 YAML 文件,然后一条命令搞定一切。这篇就来带你入门 Compose,把 Flask + Redis 计数器应用的启动过程从"手动敲 8 条命令"变成"一条 docker compose up"。

一、Compose 是什么?解决什么问题?

Docker Compose 是 Docker 官方推出的多容器应用编排工具,核心价值就是用声明式的 YAML 文件描述整个应用栈,包括服务、网络、数据卷的配置,然后通过一条命令统一管理所有服务的生命周期。

看一下我们第 10 篇手动操作的痛点,以及 Compose 是如何一一解决的:

二、V1 vs V2 vs V3:我该用哪个?

在开始写配置文件之前,有必要弄清楚版本号的问题。

Docker Compose 文件格式经历了多次演变:V1 格式(docker-compose.yml,无 version 字段)是早期版本,已经彻底废弃;V2 格式引入了 version: '2.x',支持命名卷和网络;V3 格式(version: '3.x')增加了 Swarm 部署相关配置。

但现在(2024 年起)Docker 官方已弃用version 字段。使用 docker compose(V2 命令,中间是空格,不是横杠)时,直接编写不带 version 的 YAML 文件即可,Docker 会自动使用 Compose Specification 规范解析。如果你看到一些教程还在使用 version: '3',那是历史遗留写法,功能上仍然可用,但官方推荐不再写 version

本系列全部采用最新的 Compose Specification 格式(无 version 字段),命令使用 docker compose(空格版)

三、编写第一个 docker-compose.yml

把第 10 篇的启动流程"翻译"成 Compose 文件。在项目根目录下新建 docker-compose.yml

# ============================================================
# Flask + Redis 计数器应用 —— Docker Compose 配置文件
# 系列贯穿案例
# ============================================================
services:
  # ---- Redis 服务 ----
  redis:
    image: redis:alpine
    container_name: redis
    restart: unless-stopped
    command: redis-server --appendonly yes
    volumes:
      - redis-data:/data
    networks:
      - app-net
    healthcheck:
      test: ["CMD", "redis-cli", "ping"]
      interval: 10s
      timeout: 3s
      retries: 3
      start_period: 5s
  # ---- Flask 应用服务 ----
  flask-app:
    image: flask-redis-counter:2.0
    # 如果镜像不在本地,可以改为 build: . 来从 Dockerfile 构建
    container_name: flask-app
    restart: unless-stopped
    ports:
      - "5000:5000"
    volumes:
      - flask-logs:/app/logs
    networks:
      - app-net
    depends_on:
      redis:
        condition: service_healthy
    healthcheck:
      test: ["CMD", "curl", "-f", "http://localhost:5000/health"]
      interval: 30s
      timeout: 3s
      start_period: 5s
      retries: 3
# ---- 数据卷 ----
volumes:
  redis-data:
  flask-logs:
# ---- 网络 ----
networks:
  app-net:
    driver: bridge

3.1 文件结构拆解

Compose 文件包含三个顶级元素:

services:定义应用栈中每个服务的配置。每个服务相当于一个 docker run 命令的完整参数集合。当前定义了两个服务——redisflask-app。在 Compose 管理的网络中,服务名(redisflask-app)会自动作为 DNS 记录,其他服务可以通过服务名直接访问。这就是为什么 app.py 里写的 host='redis' 能直接工作——Compose 自动创建了 DNS 解析。

volumes:声明命名卷。与手动执行 docker volume create 创建的效果完全一致,但由 Compose 统一管理生命周期。docker compose down 时默认不会删除 volumes(防止误删数据),如需删除需加 -v 参数。

networks:声明网络。driver: bridge 表示创建自定义 bridge 网络,与第 8 篇手动执行 docker network create app-net 的效果完全一致。

3.2 depends_on 的两种写法

depends_on 有两种用法,效果差异很大:

简单写法(仅控制启动顺序)

这种写法只保证 redis 容器先启动,但不等待 Redis 服务就绪——redis 容器可能处于 “Up” 状态但 Redis 进程还在加载数据,此时 Flask 连接 Redis 会失败。

条件写法(等待健康检查通过)

depends_on:
  redis:
    condition: service_healthy

这是我们现在用的写法:condition: service_healthy 表示不仅要等 redis 容器启动,还要等它的健康检查通过redis-cli ping 返回 PONG),才会启动 flask-app。这个 service_healthy 条件引入了 Compose v2.1+ 规范,到 Compose v3 曾被标记为 deprecated,但在最新的 Compose Specification 中又正式回归。使用 docker compose 命令即可正常使用,完全不需要 version 字段。

四、核心命令:从 up 到 down

4.1 docker compose up:一键启动

# 前台启动(可以看到所有服务的日志交错输出)
docker compose up

# 后台启动(推荐日常使用)
docker compose up -d

输出:

[+] Running 3/3
 ✔ Network flask-redis-counter_app-net    Created    0.1s
 ✔ Volume "flask-redis-counter_redis-data"  Created    0.0s
 ✔ Volume "flask-redis-counter_flask-logs"  Created    0.0s
 ✔ Container redis                         Started    0.5s
 ✔ Container flask-app                     Started    1.2s

注意两个细节:第一,网络和卷的名称会自动带上项目名(默认是当前目录名,这里是 flask-redis-counter)作为前缀,避免不同项目之间的资源名称冲突。第二,docker compose up -d 仅启动服务,不会重新构建镜像。如果你修改了 Dockerfile 或代码,需要先 docker compose buildup,或者直接用 docker compose up --build -d

4.2 查看服务状态

输出:

NAME        IMAGE                        COMMAND                  SERVICE     STATUS                    PORTS
flask-app   flask-redis-counter:2.0     "python app.py"          flask-app   running (healthy)         0.0.0.0:5000->5000/tcp
redis       redis:alpine                "docker-entrypoint.s…"   redis       running (healthy)         6379/tcp

注意两点:docker compose ps 只会显示当前项目的容器(根据 docker-compose.yml 所在目录识别项目),不会混入宿主机上其他 Docker 容器;STATUS 列标注了 (healthy),说明两个服务的 HEALTHCHECK 都已通过。

4.3 查看日志

# 查看所有服务的日志
docker compose logs

# 实时跟踪日志
docker compose logs -f

# 只看特定服务
docker compose logs flask-app

# 看最后 50 行
docker compose logs --tail=50 flask-app

docker compose logsdocker logs 最大的区别在于:前者会聚合所有服务的日志,并在每条日志前标注服务名,对于排查跨服务的调用链问题非常方便。

4.4 扩容服务

这是手动模式最难做到的事情——Compose 一条命令搞定

# 将 Flask 服务扩容到 3 个实例
docker compose up -d --scale flask-app=3

输出:

 [+] Running 3/3
 ✔ Container redis     Running    0.0s
 ✔ Container flask-app Started    0.3s
 ✔ Container flask-app-2 Started  0.4s
 ✔ Container flask-app-3 Started  0.4s

--scale 参数在 docker compose 中仅用于临时一次性扩容,不会持久化到配置文件。下次执行 docker compose up -d 时,副本数会恢复为默认的 1 个。如果需要长期使用多个副本,建议在 Compose 文件中使用 deploy.replicas(需 Swarm 模式),或直接用 K8s 的 Deployment 管理。

4.5 停止与清理

# 停止所有服务(不删除容器、网络、卷)
docker compose stop

# 启动已停止的服务
docker compose start

# 停止并删除容器(不删除网络和卷)
docker compose down

# 停止并删除容器、网络(保留卷,防止误删数据)
docker compose down --volumes
# 或简写
docker compose down -v

注意docker compose down 默认不会删除 volumes,这是出于数据安全的考虑。如果你确定要彻底清理包括数据在内的所有资源,必须显式加 -v

五、完整验证流程

# 1. 确认目录结构
ls
# app.py  docker-compose.yml  Dockerfile  requirements.txt  .dockerignore

# 2. 启动应用栈
docker compose up -d

# 3. 查看状态
docker compose ps

# 4. 测试功能
curl http://localhost:5000
# Hello World! I have been seen 1 times.
curl http://localhost:5000
# Hello World! I have been seen 2 times.

# 5. 测试健康检查
curl http://localhost:5000/health
# {"status":"ok"}

# 6. 查看聚合日志
docker compose logs --tail=20

# 7. 停止服务
docker compose down

现在,整个 Flask + Redis 应用栈的启动从第 10 篇的"手动敲 8 条命令"变成了:

一条命令,从启动 Redis、等待就绪、启动 Flask,到创建网络和数据卷,全部自动完成。

六、V1 vs V2 命令对比

Docker Compose 有两个命令版本,如果你在网上看教程,可能会遇到混用的情况。以下是区别:

如果你之前用过 docker-compose(带横杠),现在统一换为 docker compose(空格)。两者语法 99% 兼容,但 V2 在性能和功能上更优。

七、本篇总结

Docker Compose 解决的核心问题就是——把多容器应用从手动管理变成声明式管理

  • 声明式配置docker-compose.yml 一站式定义服务、网络、卷,可纳入 Git 管理
  • 一键启停docker compose up -ddocker compose down,告别冗长的手动命令
  • 健康检查驱动的启动顺序depends_on + condition: service_healthy,不再需要 sleep
  • 服务扩容--scale 参数快速测试多副本场景
  • 聚合日志:一个命令查看整个应用栈的日志,跨服务排错效率大幅提升

到此这篇关于Docker Compose入门指南之一条命令启动多服务的文章就介绍到这了,更多相关Docker Compose命令内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • 优化docker镜像体积的方法详解

    优化docker镜像体积的方法详解

    镜像的本质是镜像层和运行配置文件组成的压缩包,构建镜像是通过运行 Dockerfile 中的 RUN 、COPY 和 ADD 等指令生成镜像层和配置文件的过程,本文给大家介绍了如何优化 docker 镜像体积,需要的朋友可以参考下
    2025-03-03
  • 利用Docker-compose安装redis的简单步骤

    利用Docker-compose安装redis的简单步骤

    Docker-compose是Docker官方推出的一个工具软件,可以管理多个Docker容器组成的一个应用,下面这篇文章主要给大家介绍了关于利用Docker-compose安装redis的简单步骤,需要的朋友可以参考下
    2024-03-03
  • docker搭建kafka集群的方法实现

    docker搭建kafka集群的方法实现

    本文主要介绍了docker搭建kafka集群的方法实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2022-05-05
  • Docker容器绑定外部IP和端口的方法

    Docker容器绑定外部IP和端口的方法

    Docker允许通过外部访问容器或者容器之间互联的方式来提供网络服务。这篇文章主要介绍了Docker容器绑定外部IP和端口的方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-12-12
  • 减少Docker镜像大小的10个优化技巧

    减少Docker镜像大小的10个优化技巧

    当使用Docker时,镜像大小是一个很大的问题,下面这篇文章主要给大家介绍了关于减少Docker镜像大小的10个优化技巧,文中通过代码介绍的非常详细,需要的朋友可以参考下
    2024-01-01
  • Docker 1分钟搭建DNS服务器的方法

    Docker 1分钟搭建DNS服务器的方法

    本篇文章介绍了Docker 1分钟搭建DNS服务器的方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2017-12-12
  • Docker容器host与none网络的使用

    Docker容器host与none网络的使用

    本文主要介绍了Docker容器host与none网络的使用,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧<BR>
    2022-06-06
  • Centos7 安装部署Kubernetes(k8s)集群实现过程

    Centos7 安装部署Kubernetes(k8s)集群实现过程

    这篇文章主要为大家介绍了Centos7 安装部署Kubernetes(k8s)集群实现过程详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2022-11-11
  • docker容器调用yum报错的解决办法

    docker容器调用yum报错的解决办法

    在本篇文章里小编给大家分享的是关于docker容器调用yum报错的解决办法,有兴趣的朋友们可以参考下。
    2020-03-03
  • docker如何查询镜像版本信息

    docker如何查询镜像版本信息

    这篇文章主要介绍了docker如何查询镜像版本信息问题,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2023-03-03

最新评论