Docker--Docker Swarm集群
Docker Swarm 是docker原生集群管理系统,它将一个Docker主机池变成了一个虚拟主机,只需要使用简单的API就可以实现与Docker集群的通信。
从Docker 1.12.0开始,Docker Swarm就内置于Docker引擎中了,不需要单独安装配置。
节点架构
无标题
swarm node
从物理上讲,一个swarm 就是若干个安装了Docker的物理机或虚拟机,这些主机上的Docker 都采用Swarm 模式运行。
从逻辑上讲,一个Swarm 由若干个节点node组成,每个node会落实在一个物理Docker主机上,但是一个物理Docker主机不一定就是一个node,也可能一个主机上有多个node节点,即swarm node与Docker主机不是一对一关系。
swarm node 有两种类型:manager和worker。
Manager
Manager节点用于维护swarm集群状态、调试service、处理swarm集群管理任务。为了防止单点故障,一个swarm集群一般包含多个manager,这些Manager通过Raft算法为维护着一致性。
Worker
Worker节点用于在其Container 中运行task任务,即对外提供service服务。默认manager 同时也充当worker角色,可以运行task任务。
角色转换
manager 和Worker 的角色不是一成不变的,他们之间可以相互转换。
manager–》worker 称为节点降级
worker–》manager 称为节点升级
服务架构
无标2题
无标3题
service
搭建docker swarm的目的是为了在swarm集群中运行应用,提供更强抗压能力的服务。
service服务是一个逻辑概念,表示对外提供的服务。
task
一个service是通过task的形式出现在swarm 的各个节点中,每个节点的task是通过容器对外提供服务。
编排器
在swarm manager中有一个编排器,用来管理task的创建与停止。比如:
searm manager 中定义一个有3个task的service时,
编排器会先创建3个task,每个task有一个taskID,通过分配器为每个task分配一个虚拟IP。
再讲task注册到内置的DNS中。当某个task不可用时,编排器会在DNS中注销该task。
分发器
swarm manager中有一个分发器,用于对task的监听、调度等操作。
在前面的例子中,当编排器创建3个task后,会调用分发器为每个task分配节点,
分发器会现在swarm集群的所有节点中找到3个 available node,每个node分配一个task。每个task像是一个“插槽”,分发器会在每个“插槽”中放入一个容器,一个容器就是一个task实例。
一旦容器运行,分发器就能监测其运行状态,即task的运行状态。
如果容器不可用或被终止,task也会被终止。此时编排器会立即在DNS中注销该task,然后编排器再生成一个新的task,并在DNS中注册,然后分发器分配一个新的available node ,然后在此节点上运行容器。
分发器除了为task分配节点外,还实现对访问请求的负载均衡。当请求到来时,会被manager处理:根据内置的DNS,实现访问的负载均衡。
服务部署模式
无4标题
常见的service部署模式有两种:replicated模式与global模式
replicated模式:副本模式,service的默认部署模式,需要指定task数量。当task数量不等于swarm 的节点数量时,需要使用replicated模式。
manager 中的分发器会找到task个数的available node,为每个节点分配一个或若干个task。
global模式:全局模式,分发器为每个节点都分配一个task。不能指定task数量。swarm集群每增加一个节点,编排器就会创建一个task,通过分发器分配到新的节点上。
swarm集群搭建
现在搭建一个swarm集群,包括5个swarm节点。
无5标题
准备5个主机,主机名分别是docker1、docker2、docker3、docker4、docker5
查看swarm激活状态
通过docker info命令查看swarm的激活状态。
无标6题
上图表示swarm未激活。
swarm初始化
在“docker1”主机上运行docker swarm init 命令。创建并初始化一个swarm
添加worker节点
复制上面执行命令的结果中添加worker节点命令在docker4和docker5中运行,将这两个节点添加未docker节点
无7标题
添加manager节点
执行docker swarm join-token manager命令
复制上面的响应结果,在docker2和docker3中运行,将这两个节点添加为manager节点
无8标题
查看swarm节点
在manager 节点docker1、docker2、docker3 上执行docker node ls 查看当前节点数据,但是在worker节点不能运行docker node ls 命令
无9标题
swarm集群维护
退出swarm集群
worker 退群:直接运行docker swarm leave 即可
worker 重新加入:先在manager运行docker swarm join-token worker
然后复制生成的命令,在新worker节点上运行,就添加到swarm集群了。
查看节点情况,发现原来的docker5是down,新的docker5节点是Ready
无标10题
删除down节点:在manager节点上运行docker node rm
manager 退群
对于manager节点,原则上不推荐直接退群,这样会导致swarm集群的一致性受到损坏。
可在docker swarm leave 命令后添加-f 或–force选项进行强制退群。
swarm自动锁定
swarm集群自动锁定原理
在manager集群中,swarm童话该国Raft日志方式维护manager集群中数据的一致性。
即每个节点通过manager间通信方式维护自己的Raft日志。
但在通信过程中有一种风险:攻击者通过Raft日志数据的传递来访问、篡改manager节点中的数据。为了防止被攻击,swarm开启了一种集群自动锁定功能,为通信启用TLS加密。加密解密的公钥与私钥全部维护在各个节点的Docker内存中。一旦节点的Docker 重启,则密钥丢失。
swarm通过autolock 标志来设置集群的自动锁定功能:true表示开启,false表示关闭。
设置自动锁定
在manager节点通过docker swarm update -autolock=true开启
此时查看manager的docker info,可以看到autolock设为true。
查看解锁密钥
在manager中运行docker swarm unlock-key查看
无标题11
关闭一个manager
直接关闭docker3 的docker引擎,模拟宕机情况
systemctl stop docker
加入manager ,启用docker3 的docker引擎
systemctl start docker
此时查看节点docker info,可以看到Swarm值为locked,若要加入,必须先解锁。
在docker3中执行docker swarm unlock命令解锁
输入密钥就完成解锁了。
swarm节点维护
角色转换
worker升级为manager
通过docker node promote命令可以将worker升级为manager。
下面的命令是将docker4和docker5升级为manager
无12标题
manager降级为worker
通过docker node demote命令将manager降级为worker
无标13题
docker node update 变更角色
通过docker node update --role [manager|worker] [node]也可以变更角色
将docker2和docker3变为manager
docker node update --role manager docker2
docker node update --role manager docker3
将docker4和docker5变为worker
docker node update --role worker docker4
docker node update --role worker docker5
节点标签
swarm可以为节点添加描述性标签,以便于更加了解节点。
添加/修改节点标签
通过docker node update --label-add命令为指定node添加key=value的标签。如果key已经存在,则修改value。如果要添加或修改多个标签,需要多个–label-add 选项指定。
docker node update --label-add auth=zs --label-add email=zs@163.com docker2
通过docker node inspect 查看该节点的标签
无标14题
删除节点标签
通过docker node update --label-rm为指定的node删除指定key标签。
若要删除多个标签,通过多个–label-rm指定要删除的key标签。
docker node update --label-rm auth --label-rm email docker2
节点删除
manage节点通过docker node rm 命令可以删除一个Down 状态的、指定的worker节点。注意:该命令只能删除worker节点,不能删除manager节点!
有问题的删除:无法直接删除Ready状态的worker节点;
无法删除manager节点。
正确的删除:首先关闭节点的Docker,是节点变为Down状态,然后再删除。
无标15题
强制删除:添加 -f选项实现强制删除!
注意:对于manager节点,强制删除也不能删除!
docker node rm -f使一个节点强制退群,而docker swarm leave是使当前docker主机关闭swarm模式。
swarm安全(PKI)
Docker内置了PKI(public key infrastructure,公钥基础设置),保障系统安全!
TLS安全保障
Swarm 节点之间采用TLS来鉴权,授权和加密通信。
当运行docker swarm init命令时,Docker 指定当前节点为一个manager节点。
manager节点生成一个新的swarm CA根证书及一对密钥。同时还会生成2个token(一个用于添加worker节点,一个用于添加manager节点)。每个token都包含CA根证书的digest个一个随机密钥。
当有节点加入Swarm时,复制manager中对应的docker swarm join 加入命令。并在该节点中运行。这个过程是通过随机密钥这种对称验证方式保障通信安全的。
无16标题
无17标题
一旦节点加入Swarm 集群,他们之间的通信都是通过TLS加密方式进行的。
先通过CA证书对通信对方的身份进行验证,在验证通过后再进行数据通信。通信数据是通过随机密钥加密过的。
CA数字证书轮换
轮换周期:Swarm的CA数字证书有可能被攻击,所以需要轮换,默认90天轮换一次。
指定证书:轮换的数字证书来自哪里呢?通过docker swarm ca命令可以指定外部ca数字证书,或生成新的CA数字证书。
轮换过程:当manager运行docker swarm ca --rotate会按顺序执行以下内容:
Docker生成一个交叉签名(cross-signed)根证书,即新根证书由旧的根证书生成的,这份交叉签名根证书是一个过渡性的根帧数。是为了确保节点仍信任旧的根帧数,也信任新的根证书。
Docker 通知所有节点立即更新根证书,这回花费几分钟时间。
所有节点更新了根证书后,manager 会通知所有节点仅信任新的根证书,不再信任旧的根证书和交叉签名根证书。
所有节点使用新的根证书签发自己的数字证书。
如果使用外部的CA根证书,那就不存在交叉签名根证书生成,直接通知所有节点更新新证书,后续过程旧与前面相同了。
manager集群容灾
热备容灾
Swarm的manager集群采用热备方式提升容灾能力。
即再manager集群中只有一个处于leader状态,其余manager处于热备状态,当manager宕机,其余manager会自动发起leader选举,重新选举一个新的manager leader。
选举算法采用Raft算法。其简单思路是,所有manager都有选举与被选举权,最后获得过半选票的manager 当选新的leader。
service创建
注意:service只能依附于docker swarm集群!所以service创建前提是swarm集群搭建完毕!
创建service
在manager中运行 docker service create 命令
比如创建一个tomcat镜像,服务名为toms,包含3个task,端口9000
docker service create --name toms --replicas 3 -p 9000:8080 tomcat:8.5.49
查看服务列表
docker service ls # 用来查看正在运行的service。一个swarm可运行多个swarm。
查看指定服务详情
docker service inspect [service name|service ID]
此时用户就可以通过swarm集群中的任意主机来访问服务了,
比如:docker3:9000或docker2:9000
查看task节点,查看指定服务的各个task所分配的节点信息
docker service ps [service name|service ID]
查看节点task
docker node ps [node]
查看节点docker5的task
docker node ps docker5
查看service日志
docker service logs [service name|service ID]
查看task日志
docker service logs [taskID]
taskID 可通过查看task详情获取
docker node ps [service name|service ID]
负载均衡
当一个service 包含多个task时,用户访问service 会通过负载均衡的方式转发给各个task处理。负载均衡策略为轮询策略,且无法通过修改service的属性方式进行变更。
但可以通过第三方实现负载均衡策略的变更,例如:Nginx、HAProxy。
service操作
task伸缩
当需要在不停止服务的前提下对服务的task进行扩容/缩容,有两种实现方式:
docker service update 方式
变更task数量
docker service update --replicas 4 toms
docker service scale 方式
变更服务数量
docker service scale toms=7
暂停节点的task分配
生产环境下,由于某主机性能低下,扩容时,不想为此主机分配更多的task,可以pause 该主机节点。
不为docker2 增加task数量
docker node update --availability pause docker2
然后就可以扩容了
docker service scale toms=10
清空task
当不想让manager节点接收task或者某个节点出现问题,需要停止服务进行维修,此时就需要将该节点上的task清空,以不影响service的整体性能。
清空docker2 节点上的task,此时就将docker2节点上task分配到其他节点了。
docker node update --availability drain docker2
task容错
当task所在主机或容器发生故障,manager编排器会自动创建新的task,然后分配到可用节点上。
service 删除
docker service rm [service name|service ID]
删除后,service消失,对应的task也全部删除。task相关的节点容器也全部消失。
滚动更新
当一个service的task较多时,为了不影响对外提供服务,对service进行更新时可采用滚动更新。
比如:将镜像tomcat:8.5.49 的service 的镜像滚动更新为tomcat:8.5.39
创建service
docker service create --name toms --replicas 10 --update-parallelism 2 --update-delay 3s --update-max-failure-ratio 0.2 --update-failure-action rollback --rollback-parallelism 2 --rollback-delay 3s \ --rollback-max-failure-ratio 0.2 --rollback-failure-action continue -p 9000:8080 tomcat:8.5.49
更新service:将镜像tomcat:8.5.49 的service 的镜像滚动更新为tomcat:8.5.39
docker service update --image tomcat:8.5.39 toms
更新回滚
当更新失败,会回滚到更新前的状态,用户也可通过命令方式手动回滚。
docker service update --rollback toms
service全局部署模式
常见的service部署模式有两种:replicated模式和global模式。
前面创建的service 是replicated模式。下来创建global模式的service。
创建service,通过–mode 指定部署模式,默认采用replicated模式。
docker service create --name toms --mode global -p 9000:8080 tomcat:8.5.49
该模式会在每个节点上分配一个task
task伸缩
对于global模式来说,要改变task数量,必须先改变该service所依附的swarm集群的节点数量。节点增加,task自动增加;节点减少,task自动减少。
比如在manager节点新增一个节点,那么这个节点会自动增加一个task。
overlay网络
overlay网络,称为重叠网络或覆盖网络,是一种构建于underlay网络之上的逻辑虚拟网络。
在物理网络的基础上,通过节点间单播隧道机制将主机两两相连而形成的虚拟、独立的网络。
Docker Swarm集群中的overlay网络 主要通过iptables、ipvs、vxlan等技术实现。
overlay网络模型
无标18题
更多推荐
所有评论(0)