Apache BookKeeper源码分析-AutoRecovery模块原理

提要

Apache Bookkeeper github地址:https://github.com/apache/bookkeeper

本源码分析基于bookkeeper 4.14版本

术语说明

0. bk: Bookkeeper中bookie节点的简称

1. ledger: Bookkeeper中分布式日志分段,由多个fragment组成

2. e : 为了简述,文中e(E)表示fragment的ensemble size,即fragment的全部可写bookie集合大小。文中部分语境e指fragment的全部可写bookie集合。

3. qw: 为了简述,文中qw(Qw)表示entry的write quorum size,即entry的写集合大小。文中部分语境qw指entry的写集合。文中entry读取时的读集合等同于写集合。

4. qa: 为了简述,文中qa(Qa)表示entry的ack quorum size,即entry写入时至少qa数量的bk返回写入成功时bk client即可认为entry写入成功。

背景

Apache Bookkeeper通过entry的多副本存储策略保证数据安全。当e=3,qw=3,qa=2时,Bookkeeper承诺entry存储的副本数为2或3。当bk宕机或下线时,必然导致该bk上的ledger中entry的副本数减1。当qa数量的bk宕机或下线时,理论上会导致数据丢失。因此Bookkeeper社区提供AutoRecovery模块保证数据存储副本数始终>=qa。

此外,在Apache Pulsar中,broker作为bk client将消息持续写入bk中。对于OPEN状态的ledger,当>=qa数量的bookie下线,如果无消息写入或者写入频次很低,会等到写入请求到来时才会触发报错创建新的ledger。如果在此之前该ledger从broker A分配到Broker B会触发recover,但ledger的多个bookie节点(>=2)已下线因此recover必定失败,出现异常ledger(即异常topic)。社区autoRecovery模块也可解决该问题。

原理

autoRecovery模块有两个主要组件:

注:下文按e=3,qw=3,qa=2策略展开

Auditor:

1. autoRecovery会选主启动Auditor,通过ledgers/underreplication/auditorelection目录下的临时节点选主,序列号最小的启动Auditor

2. 监听ledgers/available目录和ledgers/available/readonly目录,若bookie节点下线则触发审计

3. 监听ledgers/underreplication/lostBookieRecoveryDelay目录,若目录节点数据改变则触发审计

4. 审计:获取全部的ledgermetadata并按bookie进行分类(Map<BookieId, Set<ledgerId>>),将下线bookie对应的ledgers写入目录ledgers/underreplication/ledgers/,如下:

图 - 1

ReplicationWorker:

1. 各autoRecovery节点对等,每个节点单线程处理ledger

2. 从ledgers/underreplication/ledgers/(可看作等待处理的ledger队列)目录下获取一个ledger,加锁,加锁成功表示该autoRecovery可处理,加锁失败则尝试下一个ledger。

图 - 2

3. 处理ledger,可分为如下两种情况:

当ledger状态为CLOSED时,如下图,

图 - 3

a: 筛选出ledger A中entry不可读的fragment:每个fragment的entry数量可以通过后一个fragment或LastEntryId-startEntryId获得,通过percentageOfLedgerFragmentToBeVerified将这些entry分成若干等份,每份随机取一个entry作为集合B(若percentageOfLedgerFragmentToBeVerified=0则只取首尾两个entry),读取集合B的entry若读取失败则认为对应fragment需要复制,读取失败节点bk-H即是检测到的下线节点。

注:

b: 针对需要复制的fragment:从头到尾分批次读取entry,读取成功后将entry写到新的节点Bk-F

c: 修改原数据将fragment的ensemble里的Bk-H替换为Bk-F

d: 可解决影响数据丢失的风险

当ledger状态为OPEN/IN_RECOVERY时,如下图:

图 - 4

a: fragment1-3的修复同CLOSED的ledger。

b: fragment4为正在写的,若对应bookie节点都在线则无需处理。若存在bookie节点下线则需要处理:recover该open状态的ledger,目的是通过fence操作夺取broker的写权限。最后再close该ledger。

c: 可解决因bk下线或宕机导致的recover失败风险。

bk下线

如上为社区autoRecovery原理,对应社区bookie下线步骤如下:

$ bin/bookkeeper shell decommissionbookie -bookieid <lost bookieid>

该命令仅仅触发审计,并等待下线bookieid对应的ledger复制完毕。而下线bk的ledger处理则由autoRecovery完成。

如果不执行上述命令,会等待ledgers/underreplication/lostBookieRecoveryDelay配置时间触发审计。

参考文档:decomission

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容