注意
使用 include 选项需要 Docker Compose 为 2.20 (2023年7月发布)及以上版本
可使用 docker compose version 命令查看当前使用的 compose 版本

前言

Docker Compose 是管理多个容器服务的非常便捷的工具,写好一个 compose 文件即可一键启动与管理多个服务

但当要管理的服务数量较多时,单个 compose 文件难免会变得及其冗长,导致难以查阅和维护

为解决此问题,官方提供了 ExtendMerge 两种方式对 compose 进行拆分,但使用起来都不是非常的方便,也有各种各样的限制

例如冗长的启动命令

docker compose -f compose.yml -f compose.xxx.yml -f compose.yyy.yml -f compose.zzz.yml up -d

现在,官方提供了一个全新的选项 include 来更好地实现拆分


注意
docker compose 中 include 的原理类似于把被 include 文件的内容复制粘贴进当前的文件,所以与 ExtendMerge 的行为不同,同名的资源将不会被合并,而是直接报错 defines conflicting service/network,所以仅建议将 include 用于拆分文件

示例

基础示例

services:
  A:
    image: A
  B:
    image: B
  C:
    image: C

以上文件使用 include 选项可以拆分为以下文件:

# a.yml
services:
  A:
    image: nginx
# b.yml
services:
  B:
    image: nginx
# compose.yml
include:
  - a.yml
  - b.yml

services:
  C:
    image: nginx

此时使用 docker compose config 命令解析配置文件,可以看到 compose 文件被解析为了

❯ docker compose config
name: compose
services:
  A:
    image: nginx
    networks:
      default: null
  B:
    image: nginx
    networks:
      default: null
  C:
    image: nginx
    networks:
      default: null
networks:
  default:
    name: compose_default

使用 docker compose up -d 即可启动全部服务

相对路径解析示例

同时 include 选项也可以用于其他目录中的 compose 文件,相对路径都将会被解析为被 include 文件所在的路径

示例:

# ./a/compose.yml
services:
  A:
    image: nginx
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf
# ./b/compose.yml
services:
  B:
    image: nginx
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf
# ./compose.yml
include:
  - ./a/compose.yml
  - ./b/compose.yml

services:
  C:
    image: nginx
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf

使用 docker compose config 命令解析配置文件,可以看到 compose 文件被解析为了

❯ docker compose config
name: compose
services:
  A:
    image: nginx
    networks:
      default: null
    volumes:
      - type: bind
        source: path_to_compose/a/nginx.conf
        target: /etc/nginx/nginx.conf
        bind:
          create_host_path: true
  B:
    image: nginx
    networks:
      default: null
    volumes:
      - type: bind
        source: path_to_compose/b/nginx.conf
        target: /etc/nginx/nginx.conf
        bind:
          create_host_path: true
  C:
    image: nginx
    networks:
      default: null
    volumes:
      - type: bind
        source: path_to_compose/nginx.conf
        target: /etc/nginx/nginx.conf
        bind:
          create_host_path: true

networks:
  default:
    name: compose_default

个人经验

如果主 compose 文件与子 compose 文件在同一目录,可将子 compose 文件命名为 compose.xxx.yml 使其可被 VSCode 的 Docker 插件正确识别

参考

Include | Docker Docs

include top-level element