如何将 Docker Swarm 连接到多个 consul 服务器以进行故障转移?
How to connect Docker Swarm to multiple consul servers for failover?
我 运行宁 docker 蜂拥而至领事。我有一个由 3 个相互连接的节点组成的 consul 集群,用于故障转移。问题是我只能将我的 swarm worker 和 masters 连接到一个节点,如果该节点出现故障,swarm 将停止工作。那么如何将 swarm workers 和 masters 连接到我的所有节点呢?以下命令如果 运行 来自 master 将设置我的群环境连接到单个领事服务器:
#### REFERENCE
# {{master_i}} is the IP address of the master server
# {{consul_i}} is the IP address of the consul server
# {{worker_i}} is the IP address of a worker server
#### START THE MASTER
docker run --restart=unless-stopped --name=swarm-manager0 -d -p 4000:4000 swarm manage -H :4000 --replication \
--advertise {{master_0}}:4000 \
consul://{{consul_0}}:8500
#### START THE WORKERS REMOTELY FROM THE MASTER
docker -H={{worker_0}}:2375 run -d --restart=unless-stopped --name=swarm-worker0 swarm join \
--advertise={{worker_0}}:2375 \
consul://{{consul_0}}:8500/
docker -H={{worker_1}}:2375 run -d --restart=unless-stopped --name=swarm-worker1 swarm join \
--advertise={{worker_1}}:2375 \
consul://{{consul_0}}:8500/
docker -H={{worker_2}}:2375 run -d --restart=unless-stopped --name=swarm-worker2 swarm join \
--advertise={{worker_2}}:2375 \
consul://{{consul_0}}:8500/
#### START THE WORKER SERVICE DISCOVERY
docker -H={{worker_0}}:2375 run -d --restart=unless-stopped \
-h {{worker_0}} --name registrator0 -v /var/run/docker.sock:/tmp/docker.sock gliderlabs/registrator \
consul://{{consul_0}}:8500
docker -H={{worker_1}}:2375 run -d --restart=unless-stopped \
-h {{worker_1}} --name registrator1 -v /var/run/docker.sock:/tmp/docker.sock gliderlabs/registrator \
consul://{{consul_0}}:8500
docker -H={{worker_2}}:2375 run -d --restart=unless-stopped \
-h {{worker_2}} --name registrator2 -v /var/run/docker.sock:/tmp/docker.sock gliderlabs/registrator \
consul://{{consul_0}}:8500
请注意,在每个 docker 运行 命令的末尾简单地添加两个额外的 consul://{{consul_i}}:8500
(用于其他两个 consul 服务器)不会将容器连接到其他 consul 服务器.
实际上似乎没有直接开箱即用的方法; Swarm 最终(通过 libkv)获取 Consul HTTP API,它只连接到单个指定端点。更糟糕的是,如果传递了多个 Consul 主机,libkv
将抛出异常。
不过,有一种方法可以通过更多的工作来实现。如果你在每个节点 运行 Swarm 上启动一个 Consul 代理并将它们加入其中一个 Consul 服务器,它们将了解集群的状态。如果您随后将 Consul 代理的地址指定为 Swarm 的发现服务,那么 Consul 代理会将请求转发到其中一个正常运行的 Consul 服务器。
根据@slugonamission 的说法,无法将 swarm 连接到多个领事服务器的多个 IP 地址。
但是我能够创建一个位于我的领事服务器前面的 haproxy 负载平衡器。因此,我的负载均衡器将所有流量从我的负载均衡器端口 8500 转发到我所有领事服务器上的端口 8500。通过这样做,我能够使用我的负载均衡器的 IP 地址代替 {{CONSUL0}}
。这是我最基本的 haproxy.cfg
# $CONSUL0 $CONSUL0 and $CONSUL0 are the IP addresses of my consul servers
global
log 127.0.0.1 local0 notice
maxconn 2000
user haproxy
group haproxy
defaults
log global
mode http
option httplog
option dontlognull
retries 3
option redispatch
timeout connect 5000
timeout client 10000
timeout server 10000
listen appname 0.0.0.0:8500
mode http
stats enable
stats uri /haproxy?stats
stats realm Strictly\ Private
stats auth ubuntu
balance roundrobin
option httpclose
option forwardfor
server consul0 $CONSUL0:8500 check
server consul1 $CONSUL1:8500 check
server consul2 $CONSUL2:8500 check
进行更改后,我的 consul 服务器可以单独关闭,swarm 将继续工作。
另一种解决方案是 运行 每个服务器上的 consul 客户端 运行 swarm worker。然后当你创建你的 swarm worker 时,只需让他们将自己绑定到本地机器上的领事代理 运行ning:
docker run -d --restart=unless-stopped --name=swarm-client \
swarm join \
--advertise=$(hostname -i):2375 \
consul://$(hostname -i):8500/
请注意,如果本地计算机上的 consul 死亡,这将导致 swarm 崩溃。
如果你在 AWS 中部署,你可以在 ELB 后面注册 consul 服务器节点,然后将 swarm managers/nodes 指向 ELB DNS
或者,运行在所有 swarm 主机上设置一个 consul 客户端代理,并将你的 swarm managers/nodes 指向 consul 代理,即 docker0 接口 IP,172.17.0.1:8500
我 运行宁 docker 蜂拥而至领事。我有一个由 3 个相互连接的节点组成的 consul 集群,用于故障转移。问题是我只能将我的 swarm worker 和 masters 连接到一个节点,如果该节点出现故障,swarm 将停止工作。那么如何将 swarm workers 和 masters 连接到我的所有节点呢?以下命令如果 运行 来自 master 将设置我的群环境连接到单个领事服务器:
#### REFERENCE
# {{master_i}} is the IP address of the master server
# {{consul_i}} is the IP address of the consul server
# {{worker_i}} is the IP address of a worker server
#### START THE MASTER
docker run --restart=unless-stopped --name=swarm-manager0 -d -p 4000:4000 swarm manage -H :4000 --replication \
--advertise {{master_0}}:4000 \
consul://{{consul_0}}:8500
#### START THE WORKERS REMOTELY FROM THE MASTER
docker -H={{worker_0}}:2375 run -d --restart=unless-stopped --name=swarm-worker0 swarm join \
--advertise={{worker_0}}:2375 \
consul://{{consul_0}}:8500/
docker -H={{worker_1}}:2375 run -d --restart=unless-stopped --name=swarm-worker1 swarm join \
--advertise={{worker_1}}:2375 \
consul://{{consul_0}}:8500/
docker -H={{worker_2}}:2375 run -d --restart=unless-stopped --name=swarm-worker2 swarm join \
--advertise={{worker_2}}:2375 \
consul://{{consul_0}}:8500/
#### START THE WORKER SERVICE DISCOVERY
docker -H={{worker_0}}:2375 run -d --restart=unless-stopped \
-h {{worker_0}} --name registrator0 -v /var/run/docker.sock:/tmp/docker.sock gliderlabs/registrator \
consul://{{consul_0}}:8500
docker -H={{worker_1}}:2375 run -d --restart=unless-stopped \
-h {{worker_1}} --name registrator1 -v /var/run/docker.sock:/tmp/docker.sock gliderlabs/registrator \
consul://{{consul_0}}:8500
docker -H={{worker_2}}:2375 run -d --restart=unless-stopped \
-h {{worker_2}} --name registrator2 -v /var/run/docker.sock:/tmp/docker.sock gliderlabs/registrator \
consul://{{consul_0}}:8500
请注意,在每个 docker 运行 命令的末尾简单地添加两个额外的 consul://{{consul_i}}:8500
(用于其他两个 consul 服务器)不会将容器连接到其他 consul 服务器.
实际上似乎没有直接开箱即用的方法; Swarm 最终(通过 libkv)获取 Consul HTTP API,它只连接到单个指定端点。更糟糕的是,如果传递了多个 Consul 主机,libkv
将抛出异常。
不过,有一种方法可以通过更多的工作来实现。如果你在每个节点 运行 Swarm 上启动一个 Consul 代理并将它们加入其中一个 Consul 服务器,它们将了解集群的状态。如果您随后将 Consul 代理的地址指定为 Swarm 的发现服务,那么 Consul 代理会将请求转发到其中一个正常运行的 Consul 服务器。
根据@slugonamission 的说法,无法将 swarm 连接到多个领事服务器的多个 IP 地址。
但是我能够创建一个位于我的领事服务器前面的 haproxy 负载平衡器。因此,我的负载均衡器将所有流量从我的负载均衡器端口 8500 转发到我所有领事服务器上的端口 8500。通过这样做,我能够使用我的负载均衡器的 IP 地址代替 {{CONSUL0}}
。这是我最基本的 haproxy.cfg
# $CONSUL0 $CONSUL0 and $CONSUL0 are the IP addresses of my consul servers
global
log 127.0.0.1 local0 notice
maxconn 2000
user haproxy
group haproxy
defaults
log global
mode http
option httplog
option dontlognull
retries 3
option redispatch
timeout connect 5000
timeout client 10000
timeout server 10000
listen appname 0.0.0.0:8500
mode http
stats enable
stats uri /haproxy?stats
stats realm Strictly\ Private
stats auth ubuntu
balance roundrobin
option httpclose
option forwardfor
server consul0 $CONSUL0:8500 check
server consul1 $CONSUL1:8500 check
server consul2 $CONSUL2:8500 check
进行更改后,我的 consul 服务器可以单独关闭,swarm 将继续工作。
另一种解决方案是 运行 每个服务器上的 consul 客户端 运行 swarm worker。然后当你创建你的 swarm worker 时,只需让他们将自己绑定到本地机器上的领事代理 运行ning:
docker run -d --restart=unless-stopped --name=swarm-client \
swarm join \
--advertise=$(hostname -i):2375 \
consul://$(hostname -i):8500/
请注意,如果本地计算机上的 consul 死亡,这将导致 swarm 崩溃。
如果你在 AWS 中部署,你可以在 ELB 后面注册 consul 服务器节点,然后将 swarm managers/nodes 指向 ELB DNS
或者,运行在所有 swarm 主机上设置一个 consul 客户端代理,并将你的 swarm managers/nodes 指向 consul 代理,即 docker0 接口 IP,172.17.0.1:8500