doc001

Results 124 comments of doc001

> Thanks for the clarification. Would you accept a patch that possibly parallelized this operation? Of course!

这里有几个原因: - 严肃的删除这个语义在没有外围配合的情况下是做不到的。因为remove peer对被删的peer来说,是不能保证能够收到这条日志的。既然不能保证,也就无从保证删数据这个事情。 - 业务系统本身也需要记录peer的信息以做一些管理的操作,业务系统可以保证自己能够接收到删除的请求(譬如无限重试)。在实践过程中,remove peer和gc 数据推荐作为一个整体来完成,change peer 串行化。否则的话,并发的change peer 后不gc数据可能导致脑裂。 - braft并不总是知道该删什么。业务可以自定义 log storage、raft meta storage、snapshot storage,可以自行决定data存放在哪里,删除raft的数据只是整体删除副本操作的一部分。这里要么全删,不存在保留一部分的问题。 最新版本里增加了一个gc_raft_data接口,可用于删除raft部分的数据,不过对于没有使用leveldb存储vorefor小文件的情况下,也就是仅仅删除了几个目录下的文件而已。

脑裂问题的问题,我举三个例子吧。 1. 一个类似于线程安全ABA的问题。在PeerId里有一个idx字段,这个类似与一个version号,可用于区分同一机器上的同名副本。严肃的实现里**最好保证同一复制组每次创建的副本的idx不一样**,但是实际实现中,有时候比较难做到,所以会有直接都设置为0的情况。看下面这个例子: 复制组有3个副本(a, b, c),remove c 后变成 (a, b),c 副本并未看到最新的日志,它的配置停留在(a, b, c)。经过一系列复杂的变更之后,a 副本被销毁(机器维修之类的,数据被销毁),又再次在同一机器上被创建。这时候 a 如果出现异常,且日志比 c 还旧,这个副本也残留了。这时候 a、c 互相通信,c 是可以成为主的。 2. braft 提供了在极端情况下强制reset peer的运维功能。(a, b, c) 副本直接被 reset 成...

> 想请教一下, 对于采用local-merged模式,在一个目录下存放所有braft::Node的meta信息(meta uri)的情况,在删除其中一个node后,这部门meta数据要如何清理。 只能通过gc_raft_data? > > 另外, 我看gc_raft_data接口的GCOptions参数要求给出VersionedGroupId,但是version group id似乎没有对外暴露, 只能向内部实现那样自己去组装吗? `butil::string_printf(&_v_group_id, "%s_%d", _group_id.c_str(), _server_id.idx);` 第一个问题,只能通过gc_raft_data删除。 第二个问题,version 本来也是用户自己定的。理论上每次在同一个节点上新建出来同一个复制组的副本,version都应该变化,以避免混淆。

> 好的,多谢了。 > > 是不是通过braft::Node暴露一个返回VersionGroupId的util的方法会好一点,这样用户不会关心VersionGroupId的内部组织细节。 嗯,可以考虑暴露一个

有两个疑问: 1. Thread 25 看起来在等待一个 pthread 线程,需要看下被等待的线程在做什么为什么没结束,这个是关键; 2. 很多线程里有 sleep,这个是在做什么。 主要是问题1。

配置文件里加上: --raft_enable_leader_lease=true 然后在每次 leader 读之前调用一次 is_leader_lease_valid 可以保证线性一致读

> > 配置文件里加上: > > --raft_enable_leader_lease=true > > 然后在每次 leader 读之前调用一次 is_leader_lease_valid 可以保证线性一致读 > > leader apply比较快,而follower apply慢,但某个点follower当选了leader,只依赖leader的判断这个时候不能直接读吧? braft里保证了这个事情。这个lease的有效时间是从on_leader_start开始的,也就是所有的已commit数据已经全部apply完了

> > > > 配置文件里加上: > > > > --raft_enable_leader_lease=true > > > > 然后在每次 leader 读之前调用一次 is_leader_lease_valid 可以保证线性一致读 > > > > > > > > > leader apply比较快,而follower...