初探docker(三) | docker-compose 简介

本文主要介绍Docker Compose.

Docker Compose 是 Docker 官方编排(Orchestration)项目之一,负责快速的部署分布式应用。

关键词:Docker

简介

Compose定位是定义和运行多个 Docker 容器的应用(Defining and running multi-container Docker applications).

日常工作中,经常会碰到需要多个容器相互配合来完成某项任务的情况,例如要实现一个项目,除了Web服务容器本身,往往还需要再加上后端的数据库服务器,甚至包括负载均衡容器等。

Compose允许用户通过一个单独的docker-compose.yml模板文件(YAML格式)来定义一组相关联的应用容器为一个项目。

Compose有以下两个重要的概念:

  • 服务(service):一个应用的容器,实际上可以包括若干个相同镜像的容器实例。
  • 项目(project):由一组关联的应用容器组成一个完整的业务单元,在docker-compose.yml文件中定义。

Compose的默认管理对象是项目,通过子命令对项目中的一组容器进行声明周期管理.

安装

项目地址:https://github.com/docker/compose/releases

1
2
3
wget https://github.com/docker/compose/releases/latest/download/docker-compose-linux-x86_64
chmod +x docker-compose-linux-x86_64
sudo install docker-compose-linux-x86_64 /usr/local/bin/docker-compose

一个简单的场景

最常见的场景是web网站,该项目应该包含web应用和缓存。下面用Python来建立一个能够记录页面访问次数的网站。

web应用

1
2
3
4
5
6
7
8
9
10
11
12
13
from flask import Flask
from redis import Redis

app = Flask(__name__)
redis = Redis(host='redis', host=6379)

@app.route('/')
def hello():
count = redis.incr('hits')
return 'Hello World! 此页面已经被访问{}次数. \n'.format(count)

if __name__ == '__main__':
app.run(host, "0.0.0.0", debug=True)

Dockerfile

1
2
3
4
5
From python:3.6
ADD . /app
WORKDIR /app
RUN pip install redis flask
CMD ["python", "app.py"]

docker-compose.yml

1
2
3
4
5
6
7
8
version: '3'
services:
web:
build: .
ports:
- 5000:5000
redis:
image: redis

运行

1
docker-compose up -d

每访问一次5000端口,页面的次数都会+1

命令说明

大部分命令可以是项目本身,也可以是项目中的服务或者容器。如果没有特别说明,命令的对象是项目本身

命令的基本使用格式为:

1
docker-compose [-f=<arg>...] [options] [COMMAND] [ARGS...]

命令选项

  • -f, --file FILE指定使用的模板文件,默认为docker-compose.yml,可以多次指定。
  • -p, --project-name NAME指定项目名称,默认使用目录所在名称为项目名。
  • --verbose输出更多调试信息
  • -v, --version打印版本并退出。

命令使用说明

build

格式为docker-compose build [options] [SERVICE...]

构建(重新构建)项目中的服务容器。

服务容器一旦构建,将会带一个标记名。例如web项目中的一个db容器,可能是web_db

可以随时在项目目录下运行 docker-compose build来重新构建服务。

选项

  • --force-rm 删除构建过程中的临时容器。

  • --no-cache 构建镜像过程中不使用 cache(这将加长构建过程)。

  • --pull 始终尝试通过 pull 来获取更新版本的镜像。

1
2
3
4
5
6
7
8
Usage:  docker compose build [SERVICE...]
Build or rebuild services
Options:
--build-arg stringArray Set build-time variables for services.
--no-cache Do not use cache when building the image
--progress string Set type of progress output (auto, tty, plain, quiet) (default "auto")
--pull Always attempt to pull a newer version of the image.
-q, --quiet Don't print anything to STDOUT

config

验证文件格式是否正确,正确显示配置,错误显示错误原因

down

停止up命令所启动的容器,并移除网络

1
2
3
4
5
6
7
Stop and remove containers, networks

Options:
--remove-orphans Remove containers for services not defined in the Compose file.
--rmi string Remove images used by services. "local" remove only images that don't have a custom tag ("local"|"all")
-t, --timeout int Specify a shutdown timeout in seconds (default 10)
-v, --volumes volumes Remove named volumes declared in the volumes section of the Compose file and anonymous volumes attached to containers.

exec

进入指定的容器

1
2
3
4
5
6
7
8
9
10
11
 Usage: docker compose exec [options] [-e KEY=VAL...] [--] SERVICE COMMAND [ARGS...]
Execute a command in a running container.

Options:
-d, --detach Detached mode: Run command in the background.
-e, --env stringArray Set environment variables
--index int index of the container if there are multiple instances of a service [default: 1]. (default 1)
-T, --no-TTY docker compose exec Disable pseudo-TTY allocation. By default docker compose exec allocates a TTY.
--privileged Give extended privileges to the process.
-u, --user string Run the command as this user.(user or uid)
-w, --workdir string Path to workdir directory for this command.

images

列出compose文件包含的镜像

1
2
3
4
5
6
Usage:  docker compose images [SERVICE...]

List images used by the created containers

Options:
-q, --quiet Only display IDs

kill

发送SIGKILL来强制停止服务容器

支持通过-s参数指定发送的信号,默认发送SIGKILL

1
2
3
4
5
6
Usage:  docker compose kill [options] [SERVICE...]

Force stop service containers.

Options:
-s, --signal string SIGNAL to send to the container. (default "SIGKILL")

logs

查看日志

查看服务容器的输出。默认情况下,docker-compose 将对不同的服务输出使用不同的颜色来区分。可以通过 --no-color 来关闭颜色

1
2
3
4
5
6
7
8
9
10
11
12
Usage:  docker compose logs [SERVICE...]

View output from containers

Options:
-f, --follow Follow log output.
--no-color Produce monochrome output.
--no-log-prefix Don't print prefix in logs.
--since string Show logs since timestamp (e.g. 2013-01-02T13:23:37Z) or relative (e.g. 42m for 42 minutes)
--tail string Number of lines to show from the end of the logs for each container. (default "all")
-t, --timestamps Show timestamps.
--until string Show logs before a timestamp (e.g. 2013-01-02T13:23:37Z) or relative (e.g. 42m for 42 minutes)

pause

暂停一个容器

1
Usage:  docker compose pause [SERVICE...]

port

打印某个容器端口映射的公共端口

选项:

  • --protocol=proto 指定端口协议,tcp(默认值)或者 udp。

  • --index=index 如果同一服务存在多个容器,指定命令对象容器的序号(默认为 1)

1
2
3
4
5
6
7
Usage:  docker compose port [options] [--] SERVICE PRIVATE_PORT

Print the public port for a port binding.

Options:
--index int index of the container if service has multiple replicas (default 1)
--protocol string tcp or udp (default "tcp")

ps

列出项目中目前的所有容器

选项:

  • -q 只打印容器的 ID 信息。
1
2
3
4
5
6
7
8
9
10
Usage:  docker compose ps [SERVICE...]

List containers

Options:
-a, --all Show all stopped containers (including those created by the run command)
--format string Format the output. Values: [pretty | json] (default "pretty")
-q, --quiet Only display IDs
--services Display services
--status stringArray Filter services by status. Values: [paused | restarting | removing | running | dead | created | exited]

pull

拉取服务依赖的镜像

1
2
3
4
5
6
7
Usage:  docker compose pull [SERVICE...]
Pull service images

Options:
--ignore-pull-failures Pull what it can and ignores images with pull failures
--include-deps Also pull services declared as dependencies
-q, --quiet Pull without printing progress information

push

推送服务依赖的镜像到Docker镜像仓库

1
2
3
4
5
6
Usage:  docker compose push [SERVICE...]

Push service images

Options:
--ignore-push-failures Push what it can and ignores images with push failures

restart

重启项目中的服务

选项:

  • -t, --timeout TIMEOUT 指定重启前停止容器的超时(默认为 10 秒)。
1
2
3
4
5
6
Usage:  docker compose restart

Restart containers

Options:
-t, --timeout int Specify a shutdown timeout in seconds (default 10)

rm

格式为 docker-compose rm [options] [SERVICE...]

删除所有(停止状态的)服务容器。推荐先执行 docker-compose stop 命令来停止容器。

选项:

  • -f, --force 强制直接删除,包括非停止状态的容器。一般尽量不要使用该选项。
  • -v 删除容器所挂载的数据卷。
1
2
3
4
5
6
7
8
Usage:  docker rm [OPTIONS] CONTAINER [CONTAINER...]

Remove one or more containers

Options:
-f, --force Force the removal of a running container (uses SIGKILL)
-l, --link Remove the specified link
-v, --volumes Remove anonymous volumes associated with the container

run

在指定服务上执行一个命令

默认情况下,如果存在关联,则所有关联的服务将会被自动启动。除非这些服务已经在运行中。

该命令类似启动容器后运行指定的命令,相关卷、链接等等都将会按照配置自动创建。

两个不同点:

  • 给定命令将会覆盖原有的自动运行命令;
  • 不会自动创建端口,以避免冲突。

选项:

  • -d 后台运行容器。

  • --name NAME 为容器指定一个名字。

  • --entrypoint CMD 覆盖默认的容器启动指令。

  • -e KEY=VAL 设置环境变量值,可多次使用选项来设置多个环境变量。

  • -u, --user="" 指定运行容器的用户名或者 uid。

  • --no-deps 不自动启动关联的服务容器。

  • --rm 运行命令后自动删除容器,d 模式下将忽略。

  • -p, --publish=[] 映射容器端口到本地主机。

  • --service-ports 配置服务端口并映射到本地主机。

  • -T 不分配伪 tty,意味着依赖 tty 的指令将无法运行。

  • --no-deps 不自动启动关联的容器。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
Usage:  docker compose run [options] [-v VOLUME...] [-p PORT...] [-e KEY=VAL...] [-l KEY=VALUE...] SERVICE [COMMAND] [ARGS...]

Run a one-off command on a service.

Options:
-d, --detach Run container in background and print container ID
--entrypoint string Override the entrypoint of the image
-e, --env stringArray Set environment variables
-i, --interactive Keep STDIN open even if not attached. (default true)
-l, --label stringArray Add or override a label
--name string Assign a name to the container
-T, --no-TTY Disable pseudo-noTty allocation. By default docker compose run allocates a TTY
--no-deps Don't start linked services.
-p, --publish stringArray Publish a container's port(s) to the host.
--quiet-pull Pull without printing progress information.
--rm Automatically remove the container when it exits
--service-ports Run command with the service's ports enabled and mapped to the host.
--use-aliases Use the service's network useAliases in the network(s) the container connects to.
-u, --user string Run as specified username or uid
-v, --volume stringArray Bind mount a volume.
-w, --workdir string Working directory inside the container

top

查看各个服务容器运行的进程

unpause

恢复处于暂停状态的服务容器

up

创建并启动容器

该命令将自动完成包括构建镜像,(重新)创建服务,启动服务,并关联服务相关容器的一系列操作。

默认情况下,docker-compose up启动的容器在前台,控制台将会同时打印所有容器的输出信息,可以很方便进行调试。通过Ctrl-C停止命令时,所有的容器将会停止。

通过docker-compose up -d将会在后台启动并运行所有的容器。

默认情况下,如果服务容器已经存在,docker-compose将会尝试停止容器,然后重新创建(保持使用volumes-from挂载的卷),以保证新启动的服务匹配docker-compose.yml文件的最新内容。

如果用户不希望容器被停止并重新创建,可以使用docker-compose up --no-recreate。这样将只会启动处于停止状态的容器,而忽略已经运行的服务。

如果用户只想重新部署某个服务,可以使用docker-compose up --no-deps -d <SERVICE_NAME>来重新创建服务并后台停止旧服务,启动新服务,并不会影响所依赖的服务。

选项:

选项:

  • -d 在后台运行服务容器。
  • --no-color 不使用颜色来区分不同的服务的控制台输出。
  • --no-deps 不启动服务所链接的容器。
  • --force-recreate 强制重新创建容器,不能与 --no-recreate 同时使用。
  • --no-recreate 如果容器已经存在了,则不重新创建,不能与 --force-recreate 同时使用。
  • --no-build 不自动构建缺失的服务镜像。
  • -t, --timeout TIMEOUT 停止容器时候的超时(默认为 10 秒)。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
Usage:  docker compose up [SERVICE...]

Create and start containers

Options:
--abort-on-container-exit Stops all containers if any container was stopped. Incompatible with -d
--always-recreate-deps Recreate dependent containers. Incompatible with --no-recreate.
--attach stringArray Attach to service output.
--attach-dependencies Attach to dependent containers.
--build Build images before starting containers.
-d, --detach Detached mode: Run containers in the background
--exit-code-from string Return the exit code of the selected service container. Implies --abort-on-container-exit
--force-recreate Recreate containers even if their configuration and image haven't changed.
--no-build Don't build an image, even if it's missing.
--no-color Produce monochrome output.
--no-deps Don't start linked services.
--no-log-prefix Don't print prefix in logs.
--no-recreate If containers already exist, don't recreate them. Incompatible with --force-recreate.
--no-start Don't start the services after creating them.
--quiet-pull Pull without printing progress information.
--remove-orphans Remove containers for services not defined in the Compose file.
-V, --renew-anon-volumes Recreate anonymous volumes instead of retrieving data from the previous containers.
--scale scale Scale SERVICE to NUM instances. Overrides the scale setting in the Compose file if present.
-t, --timeout int Use this timeout in seconds for container shutdown when attached or when containers are already
running. (default 10)
--wait Wait for services to be running|healthy. Implies detached mode.

模板文件

Compose文件格式具有多个版本,其中版本和docker引擎的版本相关:

Compose and Docker compatibility matrix

目前最新版是3.8,以此为例:

demo

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97

version: "3.9"
services:

redis:
image: redis:alpine
ports:
- "6379"
networks:
- frontend
deploy:
replicas: 2
update_config:
parallelism: 2
delay: 10s
restart_policy:
condition: on-failure

db:
image: postgres:9.4
volumes:
- db-data:/var/lib/postgresql/data
networks:
- backend
deploy:
placement:
max_replicas_per_node: 1
constraints:
- "node.role==manager"

vote:
image: dockersamples/examplevotingapp_vote:before
ports:
- "5000:80"
networks:
- frontend
depends_on:
- redis
deploy:
replicas: 2
update_config:
parallelism: 2
restart_policy:
condition: on-failure

result:
image: dockersamples/examplevotingapp_result:before
ports:
- "5001:80"
networks:
- backend
depends_on:
- db
deploy:
replicas: 1
update_config:
parallelism: 2
delay: 10s
restart_policy:
condition: on-failure

worker:
image: dockersamples/examplevotingapp_worker
networks:
- frontend
- backend
deploy:
mode: replicated
replicas: 1
labels: [APP=VOTING]
restart_policy:
condition: on-failure
delay: 10s
max_attempts: 3
window: 120s
placement:
constraints:
- "node.role==manager"

visualizer:
image: dockersamples/visualizer:stable
ports:
- "8080:8080"
stop_grace_period: 1m30s
volumes:
- "/var/run/docker.sock:/var/run/docker.sock"
deploy:
placement:
constraints:
- "node.role==manager"

networks:
frontend:
backend:

volumes:
db-data:

以上按照顶级键的字母顺序组织,反映了compose文件本身的结构。

服务配置文件参考

默认文件路径是./docker-compose.yml

yaml和yml扩展名都可以,两者都能工作

服务定义包含应用为该服务启动的每个容器的配置,就像命令行参数传递给docker run。同样,网络和卷的定义分别类似于docker network createdocker volume create.

docker runDockerfile指定的选项:CMD一样,默认情况下会读取EXPOSEVOLUMEENV等,无需在docker-compose.yml中定义。

可以使用类似Bash的${VARIABLE}语法在配置值中使用环境变量:参考变量替换

在Docker Compose中使用GPU

旧版docker compose
1
2
3
4
5
6
services:
test:
image: nvidia/cuda:10.2-base
command: nvidia-smi
runtime: nvidia

新版本

使用指定数目的GPU

1
2
3
4
5
6
7
8
9
10
11
services:
test:
image: nvidia/cuda:10.2-base
command: nvidia-smi
deploy:
resources:
reservations:
devices:
- driver: nvidia
count: 1
capabilities: [gpu]

使用全部的GPU

1
2
3
4
5
6
7
8
9
10

services:
test:
image: tensorflow/tensorflow:latest-gpu
command: python -c "import tensorflow as tf;tf.test.gpu_device_name()"
deploy:
resources:
reservations:
devices:
- capabilities: [gpu]