Docker服务编排03-Docker Swarm

10 篇文章 4 订阅

目录

一。Docker Swarm简介

二。Docker Swarm部署集群

2.1.Swarm配置集群节点

2.1.1 Swarm组织集群

2.1.2 docker swarm 过滤

2.1.3 Swarm常见运维问题

2.1.4 Swarm日志

2.2.Docker Swarm部署集群服务

2.2.1 docker serivce 部署单个集群

2.2.2 docker stack部署多个集群

2.3.Docker Swarm可视化工具

2.3.1 可视化工具visualizer

2.3.2 可视化管理工具portainer


一。Docker Swarm简介

 Swarm是Docker公司推出的用来管理docker集群,它将一群Docker宿主机变成一个单一的,虚拟的主机。Swarm使用标准的Docker API接口作为其前端访问入口,换言之,各种形式的Docker Client(docker client in Go, docker_py, docker等)均可以直接与Swarm通信。Swarm几乎全部用go语言来完成开发,Swarm0.2发布,相比0.1版本,0.2版本增加了一个新的策略来调度集群中的容器,使得在可用的节点上传播它们,以及支持更多的Docker命令以及集群驱动。
  Swarm deamon只是一个调度器(Scheduler)加路由器(router),Swarm自己不运行容器,它只是接受docker客户端发送过来的请求,调度适合的节点来运行容器,这意味着,即使Swarm由于某些原因挂掉了,集群中的节点也会照常运行,当Swarm重新恢复运行之后,它会收集重建集群信息.

Swarm架构:  

Swarm 集群中每台 Docker 主机称为一个节点。其中主动初始化一个 Swarm 集群的节点称为管理节点(Manager),加入一个Swarm 集群的节点称为工作节点(Worker Node)。工作节点是任务执行节点,管理节点将任务下发至工作节点执行。管理节点默认也作为工作节点。一个 Swarm 集群可以有多个管理节点,但只有一个管理节点可以成为 leader。

结构图

 

Docker Swarm 和 Docker Compose 一样,都是 Docker 官方容器编排项目,但不同的是,Docker Compose 是一个在单个服务器或主机上创建多个容器的工具,而 Docker Swarm 则可以在多个服务器或主机上创建容器集群服务,对于微服务的部署,显然 Docker Swarm 会更加适合。

从 Docker 1.12.0 版本开始,Docker Swarm 已经包含在 Docker 引擎中(docker swarm),并且已经内置了服务发现工具

Docker Swarm操作集群步骤

  1. Docker Machine 创建 Docker 主机(开放远程2375端口 安装docker),也可以使用物理主机安装docker
    修改 /lib/systemd/system/docker.service 在ExecStart添加-H tcp://0.0.0.0:2375 -H unix:///var/run/docker.sock \  执行sytemctl daemon-reload重启
  2. Docker Swarm 配置集群节点
  3. Docker Service 部署单个集群服务
  4. Docker Stack 部署多个集群服务,以及 GUI 管理页面

内部组件详细结构图:

二。Docker Swarm部署集群

规划主机
  

2.1.Swarm配置集群节点

2.1.1 Swarm组织集群

创建集群(docker swarm init)
   docker swarm init命令详解参考官网 docker swarm init | Docker Documentation

[root@swarm01 ~]# docker swarm init --advertise-addr 192.168.58.144
Swarm initialized: current node (94y1aq5dfazm5bpppc5t0zi06) is now a manager.

To add a worker to this swarm, run the following command:

    docker swarm join \
    --token SWMTKN-1-5c8fhbllao1tw97wn1ob7vytxnlw0b1kezcqqquo6k0qe5m1lu-3h1xt77env6excdy78q1qnlvo \
    192.168.58.144:2377

To add a manager to this swarm, run 'docker swarm join-token manager' and follow the instructions.

新增成功后 日志中就有添加到集群的命令,同时查看节点
  主键编号                      -               主机名    -     状态   -  是否激活(Active激活)-目前角色(leader就是管理者)

[root@swarm01 ~]# docker node ls
ID                           HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
94y1aq5dfazm5bpppc5t0zi06 *  swarm01   Ready   Active        Leader

 其他两台主机使用新建集群中日志的docker swarm join 语句加入集群
  docker swarm join 详细参考docker swarm join | Docker Documentation
  退出集群 docker swarm leave(worker)  master退出 docker swarm leave --force

[root@swarm03 ~]# docker swarm join \
>     --token SWMTKN-1-5c8fhbllao1tw97wn1ob7vytxnlw0b1kezcqqquo6k0qe5m1lu-3h1xt77env6excdy78q1qnlvo \
>     192.168.58.144:2377
This node joined a swarm as a worker.

如果推出了join界面可以通过以下命令查看

 docker swarm join-token worker

管理机器继续查看节点(一个leader)

[root@swarm01 ~]# docker node ls   
ID                           HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
74zhsvy6te3xbn4zmmct5dgno    swarm02   Ready   Active        
7lg833q1b8ur3iayuvpp50umy    swarm03   Ready   Active        
94y1aq5dfazm5bpppc5t0zi06 *  swarm01   Ready   Active        Leader

145机器提升为leader(注意只有一个leader处于激活状态,其他leader高可用standby)
  docker node详细命令参考docker node | Docker Documentation

[root@swarm01 ~]# docker node promote swarm02
Node swarm02 promoted to a manager in the swarm.
[root@swarm01 ~]# docker node ls
ID                           HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
74zhsvy6te3xbn4zmmct5dgno    swarm02   Ready   Active        Reachable
7lg833q1b8ur3iayuvpp50umy    swarm03   Ready   Active        
94y1aq5dfazm5bpppc5t0zi06 *  swarm01   Ready   Active        Leader

2.1.2 docker swarm 过滤

docker swarm有两种角色 manager和worker,使用 promote节点自动从worker角色升级为manager 通过ls过滤
角色属于过滤机制的一种

[root@swarm01 ~]# docker node ls --filter role=worker
ID                         HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
7lg833q1b8ur3iayuvpp50umy  swarm03   Ready   Active        
[root@swarm01 ~]# docker node ls --filter role=manager
ID                           HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
74zhsvy6te3xbn4zmmct5dgno    swarm02   Ready   Active        Reachable
94y1aq5dfazm5bpppc5t0zi06 *  swarm01   Ready   Active        Leader

 将swarm02节点降级为worker节点

[root@swarm01 ~]# docker node update swarm02 --role=worker
swarm02
[root@swarm01 ~]# docker node ls
ID                           HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
74zhsvy6te3xbn4zmmct5dgno    swarm02   Ready   Active        
7lg833q1b8ur3iayuvpp50umy    swarm03   Ready   Active        
94y1aq5dfazm5bpppc5t0zi06 *  swarm01   Ready   Active        Leader

当前swarm支持的 filters 有: (docker node ls | Docker Documentation

  •  id  通过主机id过滤
    [root@swarm01 ~]# docker node ls --filter id=74
    ID                         HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
    74zhsvy6te3xbn4zmmct5dgno  swarm02   Ready   Active        
  • label node -ls --filter通过label过滤目前暂时无法过滤
     给节点添加label(lable一般是键值对的   --label-add name=db_1) 下面这个值是null
    docker node update --label-add foo swarm02

    过滤

    docker node ls -f "label=foo"

    虽然无法过滤但是通过docker node inspect可以看到已经添加label了

    [root@swarm01 ~]# docker node inspect swarm02                 
    [
        {
            "ID": "74zhsvy6te3xbn4zmmct5dgno",
            "Spec": {
                "Labels": {
                    "hello": "",
                    "myname": "node_145"
                },
                "Role": "worker",
                "Availability": "active"
            },

    删除label

    [root@swarm01 ~]# docker node update swarm02 --label-rm hello
    swarm02
    [root@swarm01 ~]# docker node update swarm02 --label-rm myname
    swarm02

  • membership 成员资格筛选器根据成员关系的存在和接受或挂起的值匹配节点
    [root@swarm01 ~]# docker node ls -f "membership=pending"
    ID                         HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
    74zhsvy6te3xbn4zmmct5dgno  swarm02   Ready   Active        
    [root@swarm01 ~]# docker node ls -f "membership=accepted"
    ID                           HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
    7lg833q1b8ur3iayuvpp50umy    swarm03   Ready   Active        
    94y1aq5dfazm5bpppc5t0zi06 *  swarm01   Ready   Active        Leader
  • name通过主机名过滤
      
    [root@swarm01 ~]# docker node ls --filter name=swarm02
    ID                         HOSTNAME  STATUS  AVAILABILITY  MANAGER STATUS
    74zhsvy6te3xbn4zmmct5dgno  swarm02   Ready   Active    

  • role 通过角色过滤 参考前面的描述
     

2.1.3 Swarm常见运维问题

1. 如果某个worker节点处于down状态一直无法连接,无论怎么重启worker节点的docker或者主机,都无法时节点处于up状态,可能需要leave然后重新join,出现

如果在worker节点无法leave
Docker Swarm 报 Error response from daemon: rpc error: code = 4 desc = context deadline exceeded

前往down状态的worker节点所在node,找到swarm的安装目录


[root@swarm-worker07-fat worker]# find / -name swarm
/run/docker/swarm
/var/lib/docker.bak/swarm
/usr/src/kernels/3.10.0-1160.2.2.el7.x86_64.debug/arch/mips/sibyte/swarm
/data/docker/docker/swarm
/data/docker/swarm

进入目录找到tasks.db

[root@swarm-worker07-fat worker]# cd /data/docker/swarm
[root@swarm-worker07-fat swarm]# ls
certificates  docker-state.json  state.json  worker
[root@swarm-worker07-fat swarm]# cd worker
[root@swarm-worker07-fat worker]# ls
tasks.db

删除tasks.db: rm -rf tasks.db
重启docker:systemctl restart docker
执行leave命令,docker swarm leave。
主节点上

docker node ls
docker node rm 节点id 删除之前旧的之后
 docker swarm join-token worker  查看主节点秘钥和命令
在worker节点重新加入即可

2.1.4 Swarm日志

查看docker进程日志

journalctl  --follow -u docker

查看服务日志

docker service logs 服务名称


 

2.2.Docker Swarm部署集群服务

2.2.1 docker serivce 部署单个集群

docker将启动在swarm集群中的容器叫做service 使用docker service命令提交服务
docker service具体详细参考:docker service create | Docker Documentation

[root@swarm01 ~]# docker service create --replicas 3 -p 8888:80 --name mynginx nginx
4obe48vuzsk68lea7zdhfh2pl
[root@swarm01 ~]# docker service ls
ID            NAME     REPLICAS  IMAGE  COMMAND
4obe48vuzsk6  mynginx  2/3       nginx  
[root@swarm01 ~]# docker service ls
ID            NAME     REPLICAS  IMAGE  COMMAND
4obe48vuzsk6  mynginx  2/3       nginx  
[root@swarm01 ~]# docker service ls
ID            NAME     REPLICAS  IMAGE  COMMAND
4obe48vuzsk6  mynginx  3/3       nginx  

 其中 --replicas表示启动该镜像的几个实例
 docker service ls查看目前已经启动的实例 2/3表示需要启动3个目前启动了两个
查看所有的nginx在worker节点的信息(docker service ps 名称)

[root@swarm01 ~]# docker service ps mynginx
ID                         NAME       IMAGE  NODE     DESIRED STATE  CURRENT STATE          ERROR
emxraij4vu4f4hnl4him6hjpw  mynginx.1  nginx  swarm01  Running        Running 3 minutes ago  
0qo34jw9hhs2ysvm8g0xav4ez  mynginx.2  nginx  swarm03  Running        Running 3 minutes ago  
6q0mluc2nce7isp65qc01o8t0  mynginx.3  nginx  swarm02  Running        Running 2 minutes ago  

分别访问 http://192.168.58.144:8888/  http://192.168.58.145:8888/ http://192.168.58.147:8888/ 发现均可以访问ngingx
移除掉nginx的service

[root@swarm01 ~]# docker service rm mynginx
mynginx

新建两个副本

docker service create --replicas 2 -p 8888:80 --name mynginx nginx

分别访问 http://192.168.58.144:8888/  http://192.168.58.145:8888/ http://192.168.58.147:8888/ 发现均可以访问ngingx
命名只部署了两个为什么却能三台机器都能访问了 
因为swarm使用了名字为ingress的overlay网络 

[root@swarm01 ~]# docker network ls
NETWORK ID          NAME                DRIVER              SCOPE
be53c597d43f        bridge              bridge              local               
60c34082957b        docker_gwbridge     bridge              local               
76a93f7787fe        host                host                local               
5y2vupi4vqq5        ingress             overlay             swarm               
74a25bcf3d4d        none                null                local    

介绍swarm网络模型:

在 Swarm Service 中有三个重要的网络概念:

  • Overlay networks 管理 Swarm 中 Docker 守护进程间的通信。你可以将服务附加到一个或多个已存在的 overlay 网络上,使得服务与服务之间能够通信。
  • ingress network 是一个特殊的 overlay 网络,用于服务节点间的负载均衡。当任何 Swarm 节点在发布的端口上接收到请求时,它将该请求交给一个名为 IPVS 的模块。IPVS 跟踪参与该服务的所有IP地址,选择其中的一个,并通过 ingress 网络将请求路由到它。
    初始化或加入 Swarm 集群时会自动创建 ingress 网络,大多数情况下,用户不需要自定义配置,但是 docker 17.05 和更高版本允许你自定义。
  • docker_gwbridge是一种桥接网络,将 overlay 网络(包括 ingress 网络)连接到一个单独的 Docker 守护进程的物理网络。默认情况下,服务正在运行的每个容器都连接到本地 Docker 守护进程主机的 docker_gwbridge 网络。
    docker_gwbridge 网络在初始化或加入 Swarm 时自动创建。大多数情况下,用户不需要自定义配置,但是 Docker 允许自定义。

swarm默认使用ingress网络查看mynginx服务

[root@swarm01 ~]# docker service inspect mynginx

其中有一段 说明ingress网络使用了vip模式并且vip是 10.255.0.6/16

"Endpoint": {
            "Spec": {
                "Mode": "vip",
                "Ports": [
                    {
                        "Protocol": "tcp",
                        "TargetPort": 80,
                        "PublishedPort": 8888
                    }
                ]
            },
            "Ports": [
                {
                    "Protocol": "tcp",
                    "TargetPort": 80,
                    "PublishedPort": 8888
                }
            ],
            "VirtualIPs": [
                {
                    "NetworkID": "5y2vupi4vqq5e5papr26n661d",
                    "Addr": "10.255.0.6/16"
                }
            ]
        },

直接到节点上查看nginx 发现屋里地址是 10.255.0.7和10.255.0.8

[root@swarm03 ~]# docker inspect 8a | grep IPA
            "SecondaryIPAddresses": null,
            "IPAddress": "",
                    "IPAMConfig": {
                    "IPAddress": "10.255.0.8",

ingress网络 只能使用 -p 提供对外的端口映射 然后访问任意一台主机负载均衡来访问容器
比如在启动一个service

docker service create --name eureka -p 8760:8761 springcloud/eureka 

如果需要在nginx服务中连接eureka就无法做到

需要在容器中互相访问可以自定义overlay网络

 docker network create --driver overlay mynetwork
[root@swarm01 ~]# docker network ls
NETWORK ID          NAME                DRIVER              SCOPE
be53c597d43f        bridge              bridge              local               
60c34082957b        docker_gwbridge     bridge              local               
76a93f7787fe        host                host                local               
5y2vupi4vqq5        ingress             overlay             swarm               
d27qf5ethd5j        mynetwork           overlay             swarm    

创建两个容器时可以指定使用自定义的mynetwork

docker service create --name eureka -p 8760:8761 --network=mynetwork springcloud/eureka 
docker service create --replicas 2 -p 8888:80 --network=mynetwork --name mynginx nginx

找到eureka的容器 docker exec -it 容器id bash进入,发现可以使用服务名来ping访问对方ip地址

root@54c0ae2b74a8:/# ping mynginx
PING mynginx (10.0.0.2): 56 data bytes
64 bytes from 10.0.0.2: icmp_seq=0 ttl=64 time=0.088 ms
64 bytes from 10.0.0.2: icmp_seq=1 ttl=64 time=0.145 ms

介绍swarm filter:

2.1.2介绍过swarm的filter 可以给node节点设置label 比如

docker node update --label-add first=w1 swarm01
docker node update --label-add first=w3 swarm03

现在如果我想在lable是first==w3的机器上安装

docker service create --name eureka -p 8760:8761 --network=mynetwork --constraint=node.labels.first==w3 springcloud/eureka 

如果我想在manager那台机器安装

[root@swarm01 ~]#  docker service create --name eureka -p 8760:8761 --network=mynetwork --constraint=node.role==manager springcloud/eureka 
80tcd3ty9uh1p9m67n2jf0aym
[root@swarm01 ~]# docker service ps eureka
ID                         NAME      IMAGE               NODE     DESIRED STATE  CURRENT STATE          ERROR
125pnqml54txpavygvmw9t2pb  eureka.1  springcloud/eureka  swarm01  Running        Running 4 seconds ago  

同理也可以使用node.id或者node.name等过滤器,完全可以自主定制

2.2.2 docker stack部署多个集群

docker service部署的是单个服务,我们可以使用docker stack进行多服务编排部署,使用的同样是docker-compose.yml配置文件,示例(部署mysql,同时部署phpadmin):

version: "2"
services:
  mysql:
    image: mariadb:5
    environment:
      MYSQL_ROOT_PASSWORD: 123456
    restart: always
    ports:
      - 3306:3306
    deploy:
      mode: replicated
      replicas: 1
  phpMyAdmin:
    image: phpmyadmin/phpmyadmin
    environment:
      PMA_HOST: 192.168.58.144
      PMA_PORT: 3306
      PMA_USER: root
      PMA_PASSWORD: 123456
    ports:
      - 8888:80
    deploy:
      mode: replicated
      replicas: 1
      placement:
        constraints: [node.role == manager]

部分老旧linux中可能docker版本比较低 没有docker stack命令,可以使用 yum -y update docker
使用命令部署(可以看到服务的名称就是 stack名字_服务名字,默认安装network 所以可以使用服务名访问
   可以使用服务名称mysql访问也可以使用 真实服务名字phpadmin_mysql访问

[root@swarm01 ~]# docker stack  deploy -c docker-compose1.yml phpadmin
Ignoring unsupported options: restart

Creating network phpadmin_default
Creating service phpadmin_phpMyAdmin
Creating service phpadmin_mysql

查看stack名字为phpadmin的所有服务

[root@swarm01 ~]# docker stack ls
NAME      SERVICES
phpadmin  2
[root@swarm01 ~]# docker stack ps phpadmin
ID            NAME                   IMAGE                         NODE     DESIRED STATE  CURRENT STATE                    ERROR  PORTS
rxyc34diyjwx  phpadmin_mysql.1       mariadb:5                     swarm03  Running        Running 28 seconds ago                  
gdu3hetdii6j  phpadmin_phpMyAdmin.1  phpmyadmin/phpmyadmin:latest  swarm01  Running        Starting less than a second ago    

访问phpadmin

2.3.Docker Swarm可视化工具

2.3.1 可视化工具visualizer

官方网站:https://github.com/dockersamples/docker-swarm-visualizer
docker镜像:Docker Hub
docker swarm安装

 docker service create \
  --name=viz \
  --publish=8080:8080/tcp \
  --constraint=node.role==manager \
  --mount=type=bind,src=/var/run/docker.sock,dst=/var/run/docker.sock \
  dockersamples/visualizer

访问 http://192.168.58.144:8080/  界面​

2.3.2 可视化管理工具portainer

官网  Container Management | Kubernetes GUI | Docker Swarm GUI | Portainer
安装文档:Deployment — Portainer 1.23.2 documentation
github:https://github.com/portainer/portainer
docker swarm安装

docker service create \
    --name portainer \
    --publish 9000:9000 \
    --replicas=1 \
    --constraint 'node.role == manager' \
    portainer/portainer

开启swarm集群每一台的远程服务 2375端口
参考 docker纪录篇4-docker使用maven远程构建_liaomin416100569的专栏-CSDN博客_maven 远程docker
访问 http://192.168.58.144:9000访问 界面1注册用户amdin,输入admin默认的密码两次, 8位以上
接下来选择remote的docker,点击connect

选择home节点列表 58.144进入

左侧菜单就可以看到58.144所有的services ,swarm集群管理等 具体自己发现

注意:
  如果使用swarm部署微服务可以使用docker stack使用overlay网络部署,因为所有容器的服务都在同一个网络中
  一般程序需要使用dockerfile打包,上传到类似harbor私服中,然后再使用docker stack部署


 

  • 2
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值