zookeeper

zk的作用

基于watcher机制异步通知的方式,注册znode,其他服务监听znode的变动,可以实现服务注册中心,集群管理,一致性协调服务等,可以降低系统的耦合。

角色

leader: 处理读写请求。写请求会转发给leader,然后由leader广播给follower,leader收到一半的ack则认为写成功了,然后持久化数据,应答客户端。
follower: 处理读请求,且参与过半投票,参与leader选举。
observer: 处理读请求,不参与过半投票和leader选举。

cap实现

zookeeper:保证了cp,写数据会让数据同步到其他节点后再返回,保证集群的数据一致性,使用zab算法,选举期间不可用。
Eureka : 保证了ap,集群各节点平等,某个节点挂了不影响集群,可能存在节点间数据不一致

有序性

更新全局有序,每次更新会生成一个唯一的时间戳。

zk脑裂处理

脑裂既本来只有一个大脑,却分裂出另外一个,导致集群混乱,zk的大脑既为leader。假设集群节点分布在两个机房,如果leader所在机房网络出问题,另一个机房中的节点可能就会重新选举leader。就会变成两个leader,即脑裂。
解决方式
zk解决脑裂的方式是通过过半选举,既选举leader需要超过一半的节点同意。那么只要保证leader处于过半的节点机房既可。尽量保证集群节点在一个网络机房内。
如果是leader故障后重新选举了leader,旧leader重启后的情况,旧leader发现自己的epoch值低于新leader则会切成follower

zab协议

zab: Zookeeper Atomic Broadcast,支持奔溃恢复的原子广播协议,适合主备系统。

主要思想:
1 通过广播数据,保证所有节点数据的一致性。
2 保证事务执行的有序性
3 保证只要规定数量的节点存活,系统就能正常运行
4 保证某个server故障重启后,数据可以恢复

具体实现:
1 数据一致性:类似二阶段提交,客户端写请求最终都会转发到leader,leader写数据需要广播到所有follower,follower接收到事务请求后写进一个队列并回复leader ack。leader得到一半以上的节点ack后,leader会提交commit请求,follower提交事务。
2 有序性:每次leader接受到写请求,会生成一个递增的事务id。
全局有序:基于tcp保证leader发出数据有序的被各follower接收。
因果有序:由于是分两段提交,有可能事务a先比事务b先创建,但是事务b先确认结束,leader先发了事务b的commit请求。事务follower有一个fifo的队列存放未提交事务,按照事务id保证接收的事务有序执行,如果接受到的commit的事务id比队列中的其他事务id都小则提交。

leader选举过程
选举leader时每台server都会参与选举,第一轮投票会先投自己,然后获取各服务器投票信息,再更新投票。此时会先比较各自的事务id zxid,谁的事务id大就选谁(事务id大的说明数据更完整),事务id一样大则比较myid,myid大的会被选举(myid是集群中的每个server的唯一id,通过服务器data目录添加一个名为myid的文件进行配置)。
选举过程中server会进入looking状态,无法提供服务。
数据同步过程
选举完新的leader后,将新的epoch发给follower, follower将更新epoch值并发送确认信号和历史事务集合给leader,leader结合所有事务集合,发送一个初始化事务集合给每个follower,follower将执行初始化事务集合中的事务(已经执行过则不会再执行)。如果旧leader恢复后,有之前执行过提交还没发给其他follower的事务,新leader要让旧leader丢弃那个事务。

事务id
即为ZXID,64位,前32位是一个纪元号epoch,后32位是一个递增的计数值。前32位是leader选举后便生成的,只有重新选举了leader之后,才会重新生成。

session机制

sessionId
客户端和zk服务端之间的连接存在会话,会话会有一个随机id。
服务端异常
如果服务端异常,导致客户端与服务端连接断开后,会尝试连接服务端集群中另一个zk,而且sessionId不会变。
客户端异常/会话超时
会话可以设置超时时间,客户端基于心跳机制会定时发送ping给服务端,当服务端在达到超时时间后还未收到客户端消息后,session会终止,此时会清除该session创建的临时数据(znode)。
超时时间大小
可以在服务端设置最大超时时间和最小超时时间,客户端要在这个时间范围内设置。

应用场景
通过zk分布式加锁(1)

多个进程往指定目录创建一个临时节点,zk能保证同时只有一个进程创建成功,创建成功表示抢到锁,其他进程没创建成功则通过watch该节点(watch只有一次有效性,服务端通知一次客户端节点发生改变后,不会再通知,客户端要重新watch),当拿到锁的线程执行结束释放锁时,可以删除节点,其他进程监听到发生改变,重新去创建节点。锁的有效期可以通过设置session的有效期实现,session过期后zk自动删除节点释放锁。
存在鲸群效应问题,竞争进程越多,需要通知的进程越多。。

通过zk分布式加锁分布式锁(2)

通过第一种方式加锁会有一种问题,如果抢锁的进程很多,那么锁释放时需要通知很多的进程,影响性能。可以通过每个进程都去创建节点的方式,以序号命名,每个进程只监听比自己序号小一个位的节点,比如2监听1,3监听2,1为当前拿到锁的,当1释放后,则会通知2,2则拿到锁。

配置发布和订阅

配置放到zk中,客户端通过zk获取配置,并watch,当数据有更新时可以收到通知并更改。

负载均衡

负载均衡,比如将分区信息注册到zk,将分区组成有序列表,从头到尾方式依次轮询达到负载均衡

命名服务

服务提供者以服务端地址创建节点,消费者通过订阅这个目录,获服务地址。
dubbo就是通过这种方式进行服务注册和消费
服务提供者启动时,通过创建临时节点,在zk /dubbo/$serviceName/providers 目录下添加服务的url。
服务消费者通过获取providers信息得到服务地址,watch改目录,以便在服务变动时接受到通知。在consumers目录写下自己的地址。
而dubbo的admin项目则只需要订阅每个服务目录既可监听每个服务的消费者和提供者信息

心跳机制

检测系统和被检测系统不直接相连,而是通过zk上的某个节点进行关联进行检测服务状态,降低系统间的耦和性。

任务分发

多个子任务往指定目录创建临时节点,并定时更新进度信息,任务管理者通过监听这些节点获取任务执行情况

集群管理和master选举

节点往zk创建一个节点目录,添加节点信息,监控系统就能知道每个节点的情况。在分布式环境下,有些业务逻辑只需要在一个机器上执行,然后其他机器共享结果即可,所以又了master机制。
master选举只需要都往制定路径创建master目录,创建成功的就能成为master。或者在同个目录下创建各自的文件,序列号最小的成为master,如果master挂了,就由当前最小的为新的master。

redis锁和zk锁对比

zk只要监控后,等通知,不用不断自己判断
客户端突然宕机,注册的znode节点自动消失,相当于释放锁,而redis则会占用锁

zk常用命令

ls / 查看zk包含的内容
ls2 / 查看zk包含的内容和更新次数等信息
create /test “testStr” 创建目录,并与testStr字符串关联
set /test “testStrs” 修改test关联的字符串内容
get /test 获取关联的文件内容
delete /test 删除目录
get /test watch 可以监听

zookeeper和eureka区别
watcher

监听机制基于与客户端建立长连接实现通知

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值