服务由多个任务实例组成,每个任务会启动一个容器。目前docker仅支持容器任务,不支持其它非容器类型的任务。服务工作原理: https://docs.docker.com/engine/swarm/how-swarm-mode-works/services/
1. 创建服务
[root@jhdocker ~]# docker service create --replicas 1 --name helloworld songcf/erlang:v1 ping www.baidu.com
7c4tyb8afww1cii57imp5rbxt
[root@jhdocker ~]# docker service ls
ID NAME REPLICAS IMAGE COMMAND
7c4tyb8afww1 helloworld 0/1 songcf/erlang:v1 ping www.baidu.com
-
docker service create
创建服务 -
--name
命名服务为helloworld -
--replicas
启动镜像/实例个数1 -
songcf/erlang:v1 ping www.baidu.com
指定镜像为:songcf/erlang:v1
,启动时执行的命令:ping www.baidu.com
服务分replicated
和global
两种类型,前者指定集群中任务实例个数;后者会在集群每个节点上运行同一任务实例,包括新加的节点。创建服务时使用--mode
指定类型,默认为replicated
。
2. 查看服务详情
查看服务详情docker service inspect --pretty
,不加 --prety
返回json格式
[root@jhdocker ~]# docker service inspect --pretty helloworld
ID: 7c4tyb8afww1cii57imp5rbxt
Name: helloworld
Mode: Replicated
Replicas: 1
Placement:
UpdateConfig:
Parallelism: 1
On failure: pause
ContainerSpec:
Image: songcf/erlang:v1
Args: ping www.baidu.com
Resources:
3. 查看服务运行于哪些节点
运行docker service ps
查看服务运行于哪些节点:
[root@jhdocker ~]# docker service ps helloworld
ID NAME IMAGE NODE DESIRED STATE CURRENT STATE ERROR
0xk66orcuu68u6ul1qw2axei9 helloworld.1 songcf/erlang:v1 localhost.localdomain Running Running 8 minutes ago
4. 缩放服务
命令docker service scale
$ docker service scale helloworld=5
helloworld scaled to 5
$ docker service scale helloworld=1
helloworld scaled to 1
运行docker service ps helloworld
查看结果
5. 删除服务
docker service rm helloworld
//然后再次查看
$ docker service inspect helloworld
[]
Error: no such service or task: helloworld
6. 滚动更新
//滚动更新服务时,更新下一个任务(容器)的延时
--update-delay 1h20m10s
//批量更新任务的数量,默认为1
--update-parallelism 1
//默认情况更新一个任务,返回`RUNNING`就会继续更新下一个,如果返回`FAILED`,更新就会停止;该参数可指定返回`FAILED`时的行为
--update-failure-action
1) 部署Redis 3.0.6
$ docker service create \
--replicas 3 \
--name redis \
--update-delay 10s \
redis:3.0.6
0u6a4s31ybk7yw2wyvtikmu50
2) 检查镜像版本
$ docker service inspect --pretty redis
ID: 0u6a4s31ybk7yw2wyvtikmu50
Name: redis
Mode: Replicated
Replicas: 3
Placement:
Strategy: Spread
UpdateConfig:
Parallelism: 1
Delay: 10s
ContainerSpec:
Image: redis:3.0.6
Resources:
3) 更新服务Redis 3.0.7
$ docker service update --image redis:3.0.7 redis
redis
调度步骤:
- 停止第一个任务
- 更新上一步停止任务
- 启动更新后的任务
- 如果返回
RUNNING
等待update-delay
指定的时间后,更新下一个任务 - 如果返回
FAILED
停止更新
4) 查看更新后的状态
执行命令docker service inspect --pretty redis
查看更新后的状态
$ docker service inspect --pretty redis
ID: 0u6a4s31ybk7yw2wyvtikmu50
Name: redis
Mode: Replicated
Replicas: 3
Placement:
Strategy: Spread
UpdateConfig:
Parallelism: 1
Delay: 10s
ContainerSpec:
Image: redis:3.0.7
Resources:
如果失败,返回信息如下
$ docker service inspect --pretty redis
ID: 0u6a4s31ybk7yw2wyvtikmu50
Name: redis
...snip...
Update status:
State: paused
Started: 11 seconds ago
Message: update paused due to failure or early termination of task 9p7ith557h8ndf0ui9s0q951b
...snip...
失败后,可重新启动更新
docker service update redis
5) 查看滚动更新后服务的状态
$ docker service ps redis
ID NAME IMAGE NODE DESIRED STATE CURRENT STATE ERROR
dos1zffgeofhagnve8w864fco redis.1 redis:3.0.7 worker1 Running Running 37 seconds
88rdo6pa52ki8oqx6dogf04fh \_ redis.1 redis:3.0.6 worker2 Shutdown Shutdown 56 seconds ago
9l3i4j85517skba5o7tn5m8g0 redis.2 redis:3.0.7 worker2 Running Running About a minute
66k185wilg8ele7ntu8f6nj6i \_ redis.2 redis:3.0.6 worker1 Shutdown Shutdown 2 minutes ago
egiuiqpzrdbxks3wxgn8qib1g redis.3 redis:3.0.7 worker1 Running Running 48 seconds
ctzktfddb2tepkr45qcmqln04 \_ redis.3 redis:3.0.6 mmanager1 Shutdown Shutdown 2 minutes ago
7. 排除节点
任务所在集群中需要删除一个节点,且将该节点上运行的任务转移到其它节点。
1) 集群中已有节点和服务如下:
$ docker service create --replicas 3 --name redis --update-delay 10s redis:3.0.6
$ docker service ps redis
ID NAME SERVICE IMAGE LAST STATE DESIRED STATE NODE
7q92v0nr1hcgts2amcjyqg3pq redis.1 redis redis:3.0.6 Running 26 seconds Running manager1
7h2l8h3q3wqy5f66hlv9ddmi6 redis.2 redis redis:3.0.6 Running 26 seconds Running worker1
9bg7cezvedmkgg6c8yzvbhwsd redis.3 redis redis:3.0.6 Running 26 seconds Running worker2
2) 排除节点
执行docker node update --availability drain
排除节点worker1
$ docker node update --availability drain worker1
worker1
3) 查看节点worker1可用状态
如下显示Availability为Drain
$ docker node inspect --pretty worker1
ID: 38ciaotwjuritcdtn9npbnkuz
Hostname: worker1
Status:
State: Ready
Availability: Drain
...snip...
4) 查看服务所在节点
如下可以看到原先worker1上的容器已停止,但任务实例还是3个,新实例在worker2中重新启动
$ docker service ps redis
ID NAME IMAGE NODE DESIRED STATE CURRENT STATE ERROR
7q92v0nr1hcgts2amcjyqg3pq redis.1 redis:3.0.6 manager1 Running Running 4 minutes
b4hovzed7id8irg1to42egue8 redis.2 redis:3.0.6 worker2 Running Running About a minute
7h2l8h3q3wqy5f66hlv9ddmi6 \_ redis.2 redis:3.0.6 worker1 Shutdown Shutdown 2 minutes ago
9bg7cezvedmkgg6c8yzvbhwsd redis.3 redis:3.0.6 worker2 Running Running 4 minutes
5) 恢复被排除的节点
执行docker node update --availability active
恢复被排除的节点,worker1的状态Availability又切换为Active
$ docker node update --availability active worker1
worker1
$ docker node inspect --pretty worker1
ID: 38ciaotwjuritcdtn9npbnkuz
Hostname: worker1
Status:
State: Ready
Availability: Active
...snip...
8. 配置运行时环境
-
--env
环境变量 -
--workdir
工作目录 -
--user
username 或 UID
$ docker service create --name helloworld \
--env MYVAR=myvalue \
--workdir /tmp \
--user my_user \
alpine ping docker.com
9uk4639qpg7npwf3fn2aasksr
9. 网络
- 创建服务时通过
--publish
命令发布容器在每个节点上的外部端口。: - 创覆盖网络:
docker network create --driver overlay my-network
,并在创建服务时,使用--network my-network
将服务附加到指定的覆盖网络,详情参考:https://docs.docker.com/engine/swarm/networking/
10. 挂载卷
有volume
和bind
两种挂载方式,创建服务时通过--mount type=volume
指定类型。
-
volume
为默认方式,参考:https://docs.docker.com/engine/reference/commandline/volume_create/ -
bind
绑定系统目录,需要确保系统目录存在,这样就不太具有移植性,所以不建议使用。