服务由多个任务实例组成,每个任务会启动一个容器。目前docker仅支持容器任务,不支持其它非容器类型的任务。服务工作原理:https://docs.docker.com/engine/swarm/how-swarm-mode-works/services/
负载均衡:假设集群有10个节点,创建的服务只在其中一个节点启动,连接另外9个节点同样会被路由过来;若10个节点都启动服务,所有客户端只连接其中一个节点,同样会被均衡的路由到10个节点。
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
[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 ago4. 缩放服务
命令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: helloworld6. 滚动更新
//滚动更新服务时,更新下一个任务(容器)的延时 --update-delay 1h20m10s //批量更新任务的数量,默认为1 --update-parallelism 1 //默认情况更新一个任务,返回`RUNNING`就会继续更新下一个,如果返回`FAILED`,更新就会停止;该参数可指定返回`FAILED`时的行为 --update-failure-action1) 部署Redis 3.0.6
$ docker service create --replicas 3 --name redis --update-delay 10s redis:3.0.6 0u6a4s31ybk7yw2wyvtikmu502) 检查镜像版本
$ 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停止更新
执行命令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 redis5) 查看滚动更新后服务的状态
$ 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 ago7. 排除节点
任务所在集群中需要删除一个节点,且将该节点上运行的任务转移到其它节点。
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 worker22) 排除节点
执行docker node update --availability drain
$ docker node update --availability drain worker1 worker13) 查看节点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 minutes5) 恢复被排除的节点
执行docker node update --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 9uk4639qpg7npwf3fn2aasksr9. 网络
- 创建服务时通过 --publish
: 命令发布容器在每个节点上的外部端口。 - 创覆盖网络: docker network create --driver overlay my-network,并在创建服务时,使用--network my-network 将服务附加到指定的覆盖网络,详情参考:https://docs.docker.com/engine/swarm/networking/
有volume和bind两种挂载方式,创建服务时通过--mount type=volume指定类型。
- volume为默认方式,参考:https://docs.docker.com/engine/reference/commandline/volume_create/
- bind绑定系统目录,需要确保系统目录存在,这样就不太具有移植性,所以不建议使用。



