微服务注册协调组件之zookeeper
zookeeper是什么
zookeeper是一个中心化的服务用来维护配置信息、命名,提供分布式的同步机制,并提供一组服务。所有这些服务被分布式系统以某种形式使用。每次实现它们时,都要进行大量的工作来修复不可避免的bug和竞争条件。由于实现这类服务的困难,应用程序最初通常会忽略它们,这使得它们在发生变化时变得脆弱,并且难以管理。即使操作正确,在部署应用程序时,这些服务的不同实现也会导致管理复杂性。
ZooKeeper的目标是将这些不同服务的精髓提炼成一个非常简单的接口,以集中协调服务。服务本身是分布式的,而且非常可靠。一致性、组管理和存在协议将由服务实现,因此应用程序不需要单独实现它们。这些应用程序的特定用途将包括zookeeper的特定组件和应用程序特定的约定的混合。ZooKeeper Recipes展示了如何使用这个简单的服务来构建更强大的抽象。
CAP原理
CAP原则又称CAP定理,指的是在一个分布式系统中,一致性(Consistency)、可用性(Availability)、分区容错性(Partition tolerance)。CAP 原则指的是,这三个要素最多只能同时实现两点,不可能三者兼顾。
一致性(C):在分布式系统中的所有数据备份,在同一时刻是否同样的值。(等同于所有节点访问同一份最新的数据副本)
可用性(A):在集群中一部分节点故障后,集群整体是否还能响应客户端的读写请求。(对数据更新具备高可用性)
分区容忍性(P):以实际效果而言,分区相当于对通信的时限要求。系统如果不能在时限内达成数据一致性,就意味着发生了分区的情况,必须就当前操作在C和A之间做出选择。分区容错的意思是,区间通信可能失败。比如,一台服务器放在中国,另一台服务器放在美国,这就是两个区,它们之间可能无法通信。
一致性算法
弱一致性(最终一致性)
DNS
Gossip(Cassandra的通信协议)
强一致性:
同步
Paxos
Raft(Multi-Paxos)
ZAB(multi-paxos)
分布式系统对fault tolorance的一般解决方案是:state machine replication(状态机)
paxos其实是一个共识算法,系统的最终一致性,不仅需要达成共识,还会取决于client的行为。
分类:
主从同步:一个节点挂,全挂。
多数派:每次写都保证大于N/2个节点,每次读保证大于N/2个读。并发顺序会影响结果
Paxos
Basic Paxos:
4个阶段,Prepare -> Promise -> Accept -> Accepted
潜在问题:存在活锁问题,提案之间不停地竞争。难实现,效率低(2轮RPC)
Multi Paxos
唯一的propser,所有请求都需要经过此leader
减少角色
Raft
分为3个子问题:
leader election:多数派,心跳包,timeout
log replication:写日志、提交
safety:失败、分区的处理方法
重新定义角色
leader
follower
candidate
原理动画解释:
http://thesecretlivesofdata.com/raft/
https://raft.github.io
解决平票的问题:随机等待一个时间后重新发起
心跳方向:leader -> follower
ZAB
原子广播协议(Zookeeper Atomic Broadcast)。基于PAXOS的改进。
角色分为:leader/follower/observer
算法基本上与Raft相同。
区别:
zab将一个leader的周期成为epoch,而raft则称之为term.
心跳方向:follower-> leader
zookeeper脑裂吗
脑裂是指在跨网络分区时,请求打到不同分区,每个分区都选出一个leader,等网络恢复时,zk不知道选哪个座位leader.
这种主要靠选举机制来保证,每次有>1/2的节点投票选择时,才能把该节点设置为leader。所以即使在跨分区的情况下,也能够保证只有一个leader。
分布式协调组件比较
组件 | 模式 | 公司 | 算法 |
---|---|---|---|
Zookeeper | CP | Apache | zab,基于Paxos算法 |
Eureka | AP | Netflix | /(开源项目已经停止维护) |
Nacos | CP + AP | 阿里巴巴 | Raft |
Consul | CP | HashiCorp | Raft |
zookeeper
基于CP。
zookeeper也可以作为注册中心,用于服务治理(zookeeper还有其他用途,例如:分布式事务锁等)
每启动一个微服务,就会去zk中注册一个临时子节点
每当有一个服务down机,由于是临时结点,此节点会立即被删除,并通知订阅该服务的微服务更新服务列表(zk上有watch,每当有节点更新,都会通知订阅该服务的微服务更新服务列表)
每当有一个新的微服务注册进来,就会在对应的目录下创建临时子节点,并通知订阅该服务的微服务更新服务列表(zk上有watch,每当有节点更新,都会通知订阅该服务的微服务更新服务列表)
每个微服务30s向zk获取新的服务列表
Eureka
基于AP。
每一个微服务中都有eureka client,用于服务的注册与发现。
当A服务需要调用B服务时,需要从eureka服务端获取B服务的服务列表,然后把列表缓存到本地,然后根据ribbon的客户端负载均衡规则,从服务列表中取到一个B服务,然后去调用此B服务当A服务下次再此调用B服务时,如果发现本地已经存储了B的服务列表,就不需要再从eureka服务端获取B服务列表,直接根据ribbon的客户端负载均衡规则,从服务列表中取到一个B服务,然后去调用B服务。
微服务,默认每30秒,就会从eureka服务端获取一次最新的服务列表
如果某台微服务down机,或者添加了几台机器,此时eureka server会通知订阅他的客户端,并让客户端更新服务列表,而且还会通知其他eureka server更新此信息
心跳检测:微服务每30秒向eureka server发送心跳。
eureka server若90s之内都没有收到某个客户端的心跳,则认为此服务出了问题,会从注册的服务列表中将其删除,并通知订阅它的客户端更新服务列表,而且还会通知其他eureka server更新此信息。
注意:Eureka的开源项目已经放弃维护,继续使用,后果自负。
Nacos
同时支持AP和CP。
阿里巴巴团队开发的服务注册于发现产品,其定义为:一个更易于构建云原生应用的动态服务发现、配置管理和服务管理平台。nacos同时支持AP和CP模式,根据服务注册临时和永久来决定AP模式还是CP模式。
对比项 | Nacos | Eureka |
---|---|---|
CAP模型 | AP和CP | AP |
客户端更新服务器信息 | 使用注册+DNS-f+健康检查模式。DNS-F客户端使用监听模式push/pull拉取更新信息 | 客户端定时轮询服务端获取其他服务ip信息并对比,相比之下服务端压力较大、延迟较大 |
伸缩性 | 使用Raft选举算法性能、可用性、容错性比较好,新加入节点无需与所有节点广播同步信息 | 由于使用广播同步信息,集群超过1000台机器后对eureka集群压力很大 |
健康检查模式 | 支持服务端/客户端/关闭检查模式,检查方式有tcp、http、sql。支持自己构建健康检查器 | 客户端向服务端发送http心跳 |
跨中心同步 | 支持 | 不支持 |
k8s集成 | 支持 | 不支持 |
分组 | Nacos可用根据业务和环境进行分组管理 | 不支持 |
权重 | Nacos默认提供权重设置功能,调整承载流量压力 | 不支持 |
总结起来,nocos相比于Eureka,具有以下特性:
Nacos具备服务优雅上下线和流量管理(API+后台管理页面),而Eureka的后台页面仅供展示,需要使用api操作上下线且不具备流量管理功能。
从部署来看,Nacos整合了注册中心、配置中心功能,把原来两套集群整合成一套,简化了部署维护
从长远来看,Eureka开源工作已停止,后续不再有更新和维护,而Nacos在以后的版本会支持
SpringCLoud+Kubernetes的组合,填补 2 者的鸿沟,在两套体系下可以采用同一套服务发现和配置管理的解决方案,这将大大的简化使用和维护的成本。同时来说,Nacos 计划实现 Service Mesh,是未来微服务的趋势
从伸缩性和扩展性来看Nacos支持跨注册中心同步,而Eureka不支持,且在伸缩扩容方面,Nacos比Eureka更优(nacos支持大数量级的集群)。
Nacos具有分组隔离功能,一套Nacos集群可以支撑多项目、多环境
Consul
基于CP.
Consul 是 HashiCorp 公司推出的开源产品,用于实现分布式系统的服务发现、服务隔离、服务配置,这些功能中的每一个都可以根据需要单独使用,也可以同时使用所有功能。Consul 官网目前主要推 Consul 在服务网格中的使用。Consul 本身使用 go 语言开发,具有跨平台、运行高效等特点,也非常方便和 Docker 配合使用。
支持 http 和 dns 协议接口。zookeeper 的集成较为复杂, etcd 只支持 http 协议。
官方提供 Web 管理界面。
1、当 Producer 启动的时候,会向 Consul 发送一个 post 请求,告诉 Consul 自己的 IP 和 Port;
2、Consul 接收到 Producer 的注册后,每隔 10s(默认)会向 Producer 发送一个健康检查的请求,检验 Producer 是否健康;
3、当 Consumer 发送 GET 方式请求 /api/address 到 Producer 时,会先从 Consul 中拿到一个存储服务 IP 和 Port 的临时表,从表中拿到 Producer 的 IP 和 Port 后再发送 GET 方式请求 /api/address;
4、该临时表每隔 10s 会更新,只包含有通过了健康检查的 Producer。
与zookeeper的区别:
Consul和 ZooKeeper、Doozerd、Etcd在架构上都非常相似,它们都有服务节点(server node),而这些服务节点的操作都要求达到节点的仲裁数(通常,节点的仲裁数遵循的是简单多数原则)。此外,它们都是强一致性的,并且提供各种语言。通过应用程序内部的客户端lib库,这些原语可以用来构建复杂的分布式系统。
Consul在一个单一的数据中心内部使用服务节点。在每个数据中心中,为了Consule能够运行,并且保持强一致性,Consul服务端需要仲裁。然而,Consul原生支持多数据中心,就像一个丰富gossip系统连接服务器节点和客户端一样。
当提供K/V存储的时候,这些系统具有大致相同的语义,读取是强一致性的,并且在面对网络分区的时候,为了保持一致性,读取的可用性是可以牺牲的。然而,当系统应用于复杂情况时,这种差异会变得更加明显。
这些系统提供的语义对开发人员构建服务发现系统很有吸引力,但更重要的是,强调开发人员要构建这些特性。ZooKeeper只提供一个原始的K/V值存储,并要求开发人员构建他们自己的系统来提供服务发现功能。相反的是,Consul提供了一个坚固的框架,这不仅仅是为了提供服务发现功能,也是为了减少推测工作和开发工作量。客户端只需简单地完成服务注册工作,然后使用一个DNS接口或者HTTP接口就可以执行工作了,而其他系统则需要你定制自己的解决方案。
一个令人信服的服务发现框架必须包含健康检测功能,并且考虑失败的可能性。要是节点失败或者服务故障了,即使开发人员知道节点A提供Foo服务也是没用的。Navie系统利用的是心跳、周期性更新和TTLs,这些系统不仅需要工作量与节点数量成线性关系,并且对服务器的固定数量提出了要求。此外,故障检测窗口的存活时间至少要和TTL一样长。
ZooKeeper提供了临时节点,这些临时节点就是K/V条目,当客户端断开连接时,这些条目会被删除。虽然这些临时节点比一个心跳系统更高级,但仍存在固有的扩展性问题,并且会增加客户端的复杂性。与ZooKeeper服务器端连接时,客户端必须保持活跃,并且去做持续性连接。此外,ZooKeeper还需要胖客户端,而胖客户端是很难编写,并且胖客户端会经常导致调试质询。
Consul使用一个完全不同的架构进行健康检测。Consul客户端可以运行在集群中的每一个节点上,而不是拥有服务器节点,这些Consul客户端属于一个gossip pool,gossip pool提供了一些功能,包括分布式健康检测。gossip协议提供了一个高效的故障检测工具,这个故障检测工具可以应用到任意规模的集群,而不仅仅是作用于特定的服务器组。同时,这个故障检测工具也支持在本地进行多种健康检测。与此相反,ZooKeeper的临时节点只是一个非常原始的活跃度检测。因为有了Consul,客户端可以检测web服务器是否正在返回200状态码,内存利用率是否达到临界点,是否有足够的数据存储盘等。此外,ZooKeeper会暴露系统的复杂性给客户端,为了避免ZooKeeper出现的这种情况,Consul只提供一个简单HTTP接口。
Consul为服务发现、健康检测、K/V存储和多数据中心提供了一流的支持。为了支持任意存储,而不仅仅是简单的K/V存储,其他系统都要求工具和lib库要率先建立。然而,通过使用客户端节点,Consul提供了一个简单的API,这个API的开发只需要瘦客户端就可以了, 而且,通过使用配置文件和DNS接口,开发人员可以建立完整的服务发现解决方案,最终,达到避免开发API的目的。
原文https://www.consul.io/intro/vs/zookeeper.html
参考文档
官网:https://zookeeper.apache.org/
一致性算法:https://www.bilibili.com/video/av21667358
Nacos官网:https://nacos.io/zh-cn/
Consul官网:https://www.consul.io/
nacos简介以及作为注册/配置中心与Eureka、apollo的选型比较:https://www.jianshu.com/p/afd7776a64c6
Consul vs Zookeeper vs Etcd vs Eureka:https://www.consul.io/intro/vs/zookeeper.html、https://blog.csdn.net/Zzhou1990/article/details/72667659?utm_medium=distribute.pc_relevant_t0.none-task-blog-BlogCommendFromMachineLearnPai2-1.nonecase&depth_1-utm_source=distribute.pc_relevant_t0.none-task-blog-BlogCommendFromMachineLearnPai2-1.nonecase、