Docker Swarm集群内部的服务发现

这篇内容探讨了Docker Swarm集群中的服务发现,解释了新Swarm模式下服务发现不再需要外部注册表,而是内置在Docker Engine中。虽然内部服务发现足够处理集群内的服务通信,但当涉及有状态服务的扩展和状态存储时,服务发现工具如Consul或etcd仍然是必要的。文章通过Docker Flow: Proxy项目展示了在扩展有状态服务时如何处理状态同步和负载均衡的挑战。
摘要由CSDN通过智能技术生成

随后的文本摘录了《 DevOps 2.1 Toolkit:Docker Swarm》一书中“ Swarm集群内部服务发现”一章。

群集群中的服务发现

旧的(独立的)Swarm需要服务注册表,以便其所有管理器都可以具有相同的群集状态视图。 当实例化旧的Swarm节点时,我们必须指定服务注册表的地址。 但是,如果您查看新Swarm的设置说明(Docker 1.12中引入了Swarm Mode),您会注意到,除了Docker Engines,我们什么都不需要。 您将找不到任何提及外部服务注册表或键值存储的内容。

这是否意味着Swarm不需要服务发现? 恰恰相反。 对服务发现的需求与以往一样强烈,因此Docker决定将其纳入Docker Engine中。 就像Swarm一样,它被捆绑在里面。 从本质上讲,内部过程仍然与独立Swarm所使用的过程非常相似,只是运动部件较少。 Docker Engine现在充当Swarm管理器,Swarm工作器和服务注册表。

将所有部件捆绑在发动机内的决定引起了不同的反应。 有人认为这样的决定会产生过多的耦合,并增加Docker Engine的不稳定程度。 其他人则认为,这种捆绑包使发动机更坚固,并为新的可能性打开了大门。 双方都有有效的论点,但我更倾向于后面一组的意见。 Docker Swarm Mode是向前迈出的一大步,如果不将引擎注册表捆绑在引擎中,是否可以实现相同的结果就值得怀疑。

重要的是要注意,捆绑在引擎中的服务注册表仅供内部使用。 我们不能访问它,也不能将其用于我们自己的目的。

了解Docker Swarm的工作原理(尤其是网络)后,您可能会想到的问题是我们是否需要服务发现(除了Swarm的内部用法)。 在DevOps 2.0 Toolkit中 ,我认为服务发现是必须的,并敦促每个人都将Consuletcd设置为服务注册表,将Registrator设置为在集群内部注册更改的机制,并敦促 Consul Templateconfd作为模板解决方案。 我们还需要那些工具吗?

我们需要服务发现吗?

在Swarm集群内部工作时,很难提供一个一般性的建议,即是否需要服务发现工具。 如果我们认为需要将服务作为这些工具的主要用例,那么答案通常是“否”。 为此,我们不需要外部服务发现。 只要应该互相通信的所有服务都在同一网络内,我们所需的就是目标服务的名称。 例如, go-demo服务查找相关数据库所需的所有操作就是其DNS是go-demo-dbDocker Swarm网络和逆向代理一章证明,对于大多数用例而言,正确的网络用法就足够了。

但是,在其中发现服务和负载均衡请求并不是发现服务的唯一原因。 我们可能还有其他用途的服务注册表或键值存储。 我们可能需要以分布式和容错的方式存储一些信息。

可以在Docker Flow:Proxy项目中看到需要键值存储的示例。 它基于具有状态服务的HAProxy。 它将信息从配置文件加载到内存中。 在动态集群中拥有有状态服务代表着需要解决的挑战。 否则,在扩展服务,发生故障后重新安排服务时,我们可能会丢失状态。

扩展有状态实例时的问题

在Swarm集群中扩展服务很容易,不是吗? 只需执行docker service scale SERVICE_NAME=NUMBER_OF_INSTANCES ,突然,该服务正在运行多个副本。

前面的陈述只是部分正确。 更精确的措辞是在Swarm集群内部扩展无状态服务很容易

扩展无状态服务之所以容易的原因在于,无需考虑任何状态。 一个实例无论运行多久都是相同的。 新实例与运行一周的实例之间没有区别。 由于状态不会随着时间变化,因此我们可以在任何给定的时刻创建新副本,并且它们将完全相同。

但是,世界不是无国籍的。 国家是我们行业不可避免的一部分。 创建第一条信息后,需要将其存储在某个位置。 我们存储数据的位置必须是有状态的。 它具有随时间变化的状态。 如果我们想扩展这样的状态服务,至少需要考虑两件事。

  1. 我们如何将一个实例的状态变化传播到其余实例?
  2. 我们如何创建有状态服务的副本(新实例),并确保状态也被复制。

我们通常将无状态和有状态服务组合到一个逻辑实体中。 后端服务可能是无状态的,并且依赖于数据库服务作为外部数据存储。 这样一来,就可以将关注点明确分开,并且每个服务的生命周期都不同。

在继续之前,我必须指出,没有使状态服务可扩展和容错的灵丹妙药。 在整本书中,我将介绍几个可能适用于您的用例的示例。 有状态服务的一个明显且非常典型的示例是数据库。 尽管存在一些常见的模式,但是几乎每个数据库都为数据复制提供了不同的机制。 这本身就足以阻止我们得出适用于所有人的明确答案。 本书稍后将探讨Mongo DB的可伸缩性。 我们还将看到Jenkins的示例,该示例将文件系统用于其状态。

我们要处理的第一种情况将是另一种类型。 我们将讨论状态存储在其配置文件中的服务的可伸缩性。 为了使事情更复杂,配置是动态的。 在服务的整个生命周期中,它会随着时间而变化。 我们将探索使HAProxy可扩展的方法。

如果我们使用官方的HAProxy映像,那么我们将面临的挑战之一就是如何更新所有实例的状态。 如何更改配置并重新加载代理的每个副本。

例如,我们可以在群集中的每个节点上挂载NFS卷,并确保在所有HAProxy容器内挂载相同的主机卷。 乍看之下,由于所有实例将共享同一配置文件,因此似乎可以解决状态问题。 主机上配置的任何更改都将在我们拥有的所有实例中可用。 但是,这本身不会改变服务的状态。

HAProxy会在初始化期间加载配置文件,而忽略了我们以后可能对配置进行的任何更改。 为了使文件状态的更改反映在服务的状态中,我们需要重新加载它。 问题在于实例可以在群集内的任何节点上运行。 最重要的是,如果我们采用动态缩放(稍后会详细介绍),我们甚至可能不知道正在运行多少实例。 因此,我们需要发现我们有多少个实例,找出它们在哪些节点上运行,获取每个容器的ID,然后才发出重新加载代理的信号。 尽管所有这些都可以编写脚本,但这远非最佳解决方案。 此外,安装NFS卷是单点故障。 如果承载该卷的服务器发生故障,则数据将丢失。 当然,我们可以创建备份,但是它们只能提供一种部分恢复丢失数据的方法。 也就是说,我们可以还原备份,但是在创建上一个备份的那一刻之间生成的数据以及节点故障将丢失。

另一种选择是将配置嵌入到HAProxy映像中。 我们可以创建一个新的基于haproxy并添加COPY指令以添加配置。 这意味着每次我们要重新配置代理时,都需要更改配置,构建一组新映像(新版本)并更新当前在集群中运行的代理服务。 可以想象,这也不实际。 对于简单的代理重新配置来说,这个过程太大了。

Docker Flow:Proxy使用了一种不同的,不太传统的方法来解决该问题。 它将状态的副本存储在Consul中。 它还使用了未记录的Swarm网络功能(至少在撰写本文时)。

DevOps 2.1工具包:Docker Swarm

封面电子书小 如果您喜欢本文,则可能对DevOps 2.1 Toolkit:Docker Swarm一书感兴趣。 与本系列的前一篇文章( DevOps 2.0工具包:使用容器化微服务自动执行持续部署管道 )提供了对一些最新DevOps实践和工具的总体了解不同,本书完全致力于Docker Swarm *及其流程和我们可能需要用来构建,测试,部署和监视集群中运行的服务的工具。

这本书仍在“发展中”。 您可以从LeanPub获取副本。 它也可以作为DevOps Toolkit系列软件包使用。 如果您现在下载它,请在其完全完成之前,获得有关新章节和更正的频繁更新。 更重要的是,您可以通过向我发送反馈意见来影响本书的发展方向。

我选择精益方法进行图书出版,因为我相信早期反馈是生产优质产品的最佳方法。 请帮助我,使本书成为任何想要采用Docker Swarm进行集群编排和调度的人的参考。

翻译自: https://www.javacodegeeks.com/2016/09/service-discovery-inside-docker-swarm-cluster.html

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值