文章出處

上一篇:Docker 三劍客之 Docker Compose

閱讀目錄:

  • Docker Machine 創建 Docker 主機
  • Docker Swarm 配置集群節點
  • Docker Service 部署單個集群服務
  • Docker Stack 部署多個集群服務,以及 GUI 管理頁面
  • docker-machine、docker swarm、docker node、docker service 和 docker stack 常用命令

Docker Swarm 和 Docker Compose 一樣,都是 Docker 官方容器編排項目,但不同的是,Docker Compose 是一個在單個服務器或主機上創建多個容器的工具,而 Docker Swarm 則可以在多個服務器或主機上創建容器集群服務,對于微服務的部署,顯然 Docker Swarm 會更加適合。

從 Docker 1.12.0 版本開始,Docker Swarm 已經包含在 Docker 引擎中(docker swarm),并且已經內置了服務發現工具,我們就不需要像之前一樣,再配置 Etcd 或者 Consul 來進行服務發現配置了。

1. Docker Machine 創建 Docker 主機

在進行 Docker Swarm 配置之前,我們還需要說下 Docker 另外一個官方工具 Docker Machine(也是 Docker 三劍客之一),其作用就是快速幫助我們搭建 Docker 主機環境,比如我們要使用 Docker Swarm,就必須有很多的 Docker 主機來進行操作,Docker Machine 就是最理想的工具。

因為我是在 Mac OS 上進行操作的,并且 Docker for Mac 已經包含了 Docker Machine(docker machine),所以我不需要再額外進行安裝了,如果使用 Linux 系統的話,安裝也非常簡單,命令:

$ sudo curl -L https://github.com/docker/machine/releases/download/v0.13.0/docker-machine-`uname -s`-`uname -m` > /usr/local/bin/docker-machine
$ sudo chmod +x /usr/local/bin/docker-machine

好了,我們先使用 Docker Machine 創建四個 Docker 主機,命令:

$ docker-machine create -d virtualbox manager1 && 
docker-machine create -d virtualbox manager2 && 
docker-machine create -d virtualbox worker1 && 
docker-machine create -d virtualbox worker2

Running pre-create checks...
(worker1) No default Boot2Docker ISO found locally, downloading the latest release...
(worker1) Latest release for github.com/boot2docker/boot2docker is v17.11.0-ce
(worker1) Downloading /Users/xishuai/.docker/machine/cache/boot2docker.iso from https://github.com/boot2docker/boot2docker/releases/download/v17.11.0-ce/boot2docker.iso...

執行上面命令,你會發現速度巨慢(如上),原因是從 GitHub 上下載一個boot2docker.iso文件(國內網絡沒辦法),怎么解決呢?很簡單,我們使用翻X的瀏覽器手動下載boot2docker.iso文件,然后拷貝到對應目錄下(我電腦的目錄/Users/xishuai/.docker/machine/cache/),然后再執行上面的命令,發現速度快的一批。

我們可以查看下創建的 Docker 主機信息,命令:

$ docker-machine ls
NAME       ACTIVE   DRIVER       STATE     URL                         SWARM   DOCKER        ERRORS
manager1   -        virtualbox   Running   tcp://192.168.99.100:2376           v17.11.0-ce   
manager2   -        virtualbox   Running   tcp://192.168.99.101:2376           v17.11.0-ce   
worker1    -        virtualbox   Running   tcp://192.168.99.102:2376           v17.11.0-ce   
worker2    -        virtualbox   Running   tcp://192.168.99.103:2376           v17.11.0-ce   

可以看到,我們創建了四個 Docker 主機(兩個 Manager 和兩個 Worker),我們還可以連接到任何一臺服務器進行操作,命令:

$ docker-machine ssh manager1
                        ##         .
                  ## ## ##        ==
               ## ## ## ## ##    ===
           /"""""""""""""""""\___/ ===
      ~~~ {~~ ~~~~ ~~~ ~~~~ ~~~ ~ /  ===- ~~~
           \______ o           __/
             \    \         __/
              \____\_______/
 _                 _   ____     _            _
| |__   ___   ___ | |_|___ \ __| | ___   ___| | _____ _ __
| '_ \ / _ \ / _ \| __| __) / _` |/ _ \ / __| |/ / _ \ '__|
| |_) | (_) | (_) | |_ / __/ (_| | (_) | (__|   <  __/ |
|_.__/ \___/ \___/ \__|_____\__,_|\___/ \___|_|\_\___|_|
Boot2Docker version 17.11.0-ce, build HEAD : e620608 - Tue Nov 21 18:11:40 UTC 2017
Docker version 17.11.0-ce, build 1caf76c

2. Docker Swarm 配置集群節點

我們執行下面命令:

$ docker-machine ssh manager1 "docker swarm init --advertise-addr 192.168.99.100"
Swarm initialized: current node (n0ub7dpn90rxjq97dr0g8we0w) is now a manager.

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

    docker swarm join --token SWMTKN-1-5uwpqibnvmho1png8zmhcw8274yanohee32jyrcjlait9djhsk-envtxo4dl6df2ar3qldcccfdg 192.168.99.100:2377

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

上面是在manager1主機上,創建一個 Docker Swarm 管理節點(初始化集群的時候,會自動把當前節點設置為管理節點)。

接著,我們在worker1worker2主機上,創建兩個工作節點,并加入到集群中,命令:

$ docker-machine ssh worker1 "docker swarm join --token SWMTKN-1-5uwpqibnvmho1png8zmhcw8274yanohee32jyrcjlait9djhsk-envtxo4dl6df2ar3qldcccfdg 192.168.99.100:2377"
This node joined a swarm as a worker.

$ docker-machine ssh worker2 "docker swarm join --token SWMTKN-1-5uwpqibnvmho1png8zmhcw8274yanohee32jyrcjlait9djhsk-envtxo4dl6df2ar3qldcccfdg 192.168.99.100:2377"
This node joined a swarm as a worker.

還有另外一個manager2主機,需要配置為管理節點,我們需要先在manager1主機上,獲取管理節點對應的token,然后再配置為管理節點,命令:

$ docker-machine ssh manager1 "docker swarm join-token manager"
To add a manager to this swarm, run the following command:

    docker swarm join --token SWMTKN-1-5uwpqibnvmho1png8zmhcw8274yanohee32jyrcjlait9djhsk-0koz1b98sco8r5cn3g61eahnu 192.168.99.100:2377

$ docker-machine ssh manager2 "docker swarm join --token SWMTKN-1-5uwpqibnvmho1png8zmhcw8274yanohee32jyrcjlait9djhsk-0koz1b98sco8r5cn3g61eahnu 192.168.99.100:2377"
This node joined a swarm as a manager.

配置好之后,我們進入manager1主機內(上面的命令也可以在主機內執行),然后查看集群節點的信息,命令:

$ docker node ls
ID                            HOSTNAME            STATUS              AVAILABILITY        MANAGER STATUS
n0ub7dpn90rxjq97dr0g8we0w *   manager1            Ready               Active              Leader
t4cy67qp0bf2spgabsutwxnzt     manager2            Ready               Active              Reachable
if0kmzp4ww3oy57y7cha7v36t     worker1             Ready               Active              
jgg61cujzaeb3du5796fm0x2g     worker2             Ready               Active       

Leader表示當然集群的頭,Reachable可以理解為頭的候選人,頭一掛掉它就頂上去了。


需要注意的是,我當天配置好之后,把所有的 Docker 主機都stop了,然后隔天重新start之后,出現了下面問題:

docker node ls
Error response from daemon: rpc error: code = Unknown desc = The swarm does not have a leader. It's possible that too few managers are online. Make sure more than half of the managers are online.

好像是集群節點丟失了頭,相關問題:如何處理 docker swarm 集群"The swarm does not have a leader"問題,按照文章進行解決:

$ docker swarm init --force-new-cluster
Error response from daemon: could not choose an IP address to advertise since this system has multiple addresses on different interfaces (10.0.2.15 on eth0 and 192.168.99.102 on eth1) - specify one with --advertise-addr
$ docker swarm init --force-new-cluster --advertise-addr 192.168.99.102
Error response from daemon: This node is not a swarm manager. Worker nodes can't be used to view or modify cluster state. Please run this command on a manager node or promote the current node to a manager.
$ docker node ls
卡死
$ docker-machine restart manager1 
重啟不了,一直轉圈

沒辦法,后來我只能刪掉四個 Docker 主機,重新進行創建了。

3. Docker Service 部署單個集群服務

在部署集群服務之前,我們需要做些準備工作,因為 Docker 主機中沒有配置 Docker 鏡像加速地址,所以在拉取官方鏡像的時候,肯定會非常慢,除了配置 Docker 鏡像加速地址之外,我們還可以使用 Docker 私有鏡像倉庫,來解決這個問題。

參考文章:Ubuntu Docker Registry 搭建私有倉庫

這邊,我再簡單說明下配置步驟,首先,在 Mac OS 上執行下面命令:

$ docker run -d -v /Users/xishuai/Documents/Docker:/var/lib/registry -p 5000:5000 --restart=always --name registry registry

$ docker tag nginx 192.168.99.1:5000/nginx:latest && 
docker push 192.168.99.1:5000/nginx:latest && 
docker pull 192.168.99.1:5000/nginx:latest

$ curl http://192.168.99.1:5000/v2/_catalog
{"repositories":["nginx"]}

我們在 Mac OS 上創建了一個私有倉庫容器,并把nginx鏡像放到私有倉庫中,因為沒有使用 Https,所以在拉取和推送鏡像的時候,會報如下錯誤(Mac OS 和 Docker 主機都會報錯):

$ docker pull 192.168.99.1:5000/nginx:latest
The push refers to a repository [192.168.99.1:5000/nginx]
Get https://192.168.99.1:5000/v1/_ping: http: server gave HTTP response to HTTPS client

解決方式,我們需要分別在四個 Docker 主機中添加配置(Docker for Mac 在管理界面配置即可),命令:

$ sudo touch /etc/docker/daemon.json && 
sudo chmod 777 /etc/docker/daemon.json && 
sudo echo '{ "insecure-registries":    ["192.168.99.1:5000"] }' > /etc/docker/daemon.json

然后重啟四個 Docker 主機(Docker for Mac 也需要重啟),命令:

$ docker-machine restart manager1 && 
docker-machine restart manager2 && 
docker-machine restart worker1 && 
docker-machine restart worker2

上面比較啰嗦,我們接下來正式部署集群服務,還是拿nginx鏡像做為示例,命令(docker service create命令詳細說明):

$ docker service create --replicas 4 -p 8088:80 --name nginx 192.168.99.1:5000/nginx:latest
ap8h8srb8yh3mni0h2nz61njz
overall progress: 4 out of 4 tasks 
1/4: running   [==================================================>] 
2/4: running   [==================================================>] 
3/4: running   [==================================================>] 
4/4: running   [==================================================>] 
verify: Service converged 

需要注意的是,--replicas 4表示創建服務的實例個數(默認是一個),啥意思?比如4,就是在四個 Docker 主機上,分別創建一個nginx服務,如果是3,那就是三個 Docker 主機,或者你可以理解為 Docker 主機的個數,另外,REPLICAS會有進度顯示,并且執行是異步的。

我們也可以手動設置實例個數,命令:

$ docker service scale nginx=4

部署好服務后,我們就可以進行查看了,命令:

$ docker service ls
ID                  NAME                MODE                REPLICAS            IMAGE                            PORTS
ap8h8srb8yh3        nginx               replicated          4/4                 192.168.99.1:5000/nginx:latest   *:8080->8080/tcp

$ docker service ps nginx
ID                  NAME                IMAGE                            NODE                DESIRED STATE       CURRENT STATE                ERROR               PORTS
l2rdrwzs5zog        nginx.1             192.168.99.1:5000/nginx:latest   manager1            Running             Running about a minute ago                       
vsfczzbwanx3        nginx.2             192.168.99.1:5000/nginx:latest   manager2            Running             Running about a minute ago                           
qtbgw5h6dsi9        nginx.3             192.168.99.1:5000/nginx:latest   worker              Running             Running about a minute ago                           
za2ejnvb3n6z        nginx.4             192.168.99.1:5000/nginx:latest   worker2             Running             Running about a minute ago

我們任意使用四個 Docker 主機中的一個 IP 地址,瀏覽器打開:http://192.168.99.100:8088/

4. Docker Stack 部署多個集群服務,以及 GUI 管理頁面

docker service部署的是單個服務,我們可以使用docker stack進行多服務編排部署,使用的同樣是docker-compose.yml配置文件,示例:

version: "3"

services:
  nginx:
    image: 192.168.99.1:5000/nginx:latest
    ports:
      - 8088:80
    deploy:
      mode: replicated
      replicas: 4

  visualizer:
    image: 192.168.99.1:5000/dockersamples/visualizer:latest
    ports:
      - "8080:8080"
    volumes:
      - "/var/run/docker.sock:/var/run/docker.sock"
    deploy:
      replicas: 1
      placement:
        constraints: [node.role == manager]

  portainer:
    image: 192.168.99.1:5000/portainer/portainer:latest
    ports:
      - "9000:9000"
    volumes:
      - "/var/run/docker.sock:/var/run/docker.sock"
    deploy:
      replicas: 1
      placement:
        constraints: [node.role == manager]

如上所示,我們總共需要部署三個服務,出了nginx服務作為示例之外,visualizer官方地址)和portainer官方地址)都是集群 GUI 管理服務。

部署命令:

$ docker stack deploy -c docker-compose.yml deploy-demo
Creating service deploy-demo_nginx
Creating service deploy-demo_visualizer
Creating service deploy-demo_portainer

部署成功之后,我們可以查看具體詳情,命令:

$ docker stack ls
NAME                SERVICES
deploy-demo         3

查看visualizerGUI 集群管理,瀏覽器打開:http://192.168.99.100:8080/

查看portainerGUI 集群管理,需要先配置賬號信息,瀏覽器打開:http://192.168.99.100:9000/

可以看到,portainervisualizer強大太多了,甚至我們所有的操作都可以在portainer上完成。

5. docker-machine、docker swarm、docker node、docker service 和 docker stack 常用命令

docker-machine 常用命令

命令 說明
docker-machine create 創建一個 Docker 主機(常用-d virtualbox
docker-machine ls 查看所有的 Docker 主機
docker-machine ssh SSH 到主機上執行命令
docker-machine env 顯示連接到某個主機需要的環境變量
docker-machine inspect 輸出主機更多信息
docker-machine kill 停止某個主機
docker-machine restart 重啟某臺主機
docker-machine rm 刪除某臺主機
docker-machine scp 在主機之間復制文件
docker-machine start 啟動一個主機
docker-machine status 查看主機狀態
docker-machine stop 停止一個主機

docker swarm 常用命令

命令 說明
docker swarm init 初始化集群
docker swarm join-token worker 查看工作節點的 token
docker swarm join-token manager 查看管理節點的 token
docker swarm join 加入集群中

docker node 常用命令

命令 說明
docker node ls 查看所有集群節點
docker node rm 刪除某個節點(-f強制刪除)
docker node inspect 查看節點詳情
docker node demote 節點降級,由管理節點降級為工作節點
docker node promote 節點升級,由工作節點升級為管理節點
docker node update 更新節點
docker node ps 查看節點中的 Task 任務

docker service 常用命令

命令 說明
docker service create 部署服務
docker service inspect 查看服務詳情
docker service logs 產看某個服務日志
docker service ls 查看所有服務詳情
docker service rm 刪除某個服務(-f強制刪除)
docker service scale 設置某個服務個數
docker service update 更新某個服務

docker stack 常用命令

命令 說明
docker stack deploy 部署新的堆棧或更新現有堆棧
docker stack ls 列出現有堆棧
docker stack ps 列出堆棧中的任務
docker stack rm 刪除堆棧
docker stack services 列出堆棧中的服務
docker stack down 移除某個堆棧(不會刪除數據)

參考資料:


文章列表


不含病毒。www.avast.com
arrow
arrow
    全站熱搜
    創作者介紹
    創作者 大師兄 的頭像
    大師兄

    IT工程師數位筆記本

    大師兄 發表在 痞客邦 留言(0) 人氣()