Docker Swarm集群中的服务发现

在旧版本Swarm中需要一个服务注册器,这样所有管理者能有一个统一的集群状态视图,因此,在初始化老版本Swarm节点时,我们需要指定服务注册器的地址,而在新版本Swarm中,也就是Docker 1.12引入的Swarm Mode,除了Docker引擎以外什么都不需要,无需额外的服务注册器或key-value存储库。

是不是Swarm不需要服务发现吗?正好相反,服务发现很重要,因此被放入Docker引擎中,Docker引擎现在扮演Swarm 管理器,Swarm工作器和服务注册器三个角色。Docker Swam Mode一个巨大进步。引擎内部服务注册器只能提供给内部用户使用。

只要所有服务在同样网络中彼此通讯,我们所需要做的是对目标服务进行命名,比如所有go-demo服务需要知道如何发现相关的数据库,那么这个目标数据库的DNS是go-demo-db。

在Swarm集群情况下(Docker Swarm),好像扩展一个服务非常方便,只要执行:
docker service scale SERVICE_NAME=NUMBER_OF_INSTANCES
这样,这个服务就会运行在多个自身复制。也即是在集群多个节点上运行。其实这种方便扩展只能说扩展无态服务很容易,因为服务没有状态,在哪个节点上运行都没有问题。

但是世界并不是无态的,状态在工程产品业界是无法避免的,状态被创建就要存储,存储状态的地方就变成有态了,状态还会经常变化,扩展有态服务需要考虑:
1.我们如何传播一个服务实例状态的变化给其他的同样的有态服务?
2.我们如何创建有状态的服务一个副本(一个新服务实例),确保状态复制准确?

我们通常混合无态和有态服务到一个逻辑实体,后端服务能够是无态的,依赖数据库服务作为外部状态存储,在这种情况下,这些服务在不同生命周期上有一个清晰的分离关注。

以前我们都认为使得有态服务扩展和容错是没有银弹的,我们看看Docker Flow:Proxy是如何处理有态服务的,其核心HAProxy就是一个有态服务,从配置文件加载配置到内存,在动态集群中包含有态服务是一个挑战,因为我们不知道有多少个有态服务实例在运行,以及运行在哪个节点上。这时我们首先需要存储有态服务实例的状态,Docker Flow将有态服务状态复制存储在Consul,Consul这是一个分布式数据库。这样解决了状态改变的广播问题和有态服务实例的状态复制问题。

Service Discovery Inside A Docker Swarm Cluster |
[该贴被banq于2016-09-20 10:04修改过]