Raft 是如何线性化的?

How is Raft linearlizable?

我是分布式系统的新手,想知道 Raft 共识算法是如何线性化的。 Raft 通过仲裁提交日志条目。在 leader Raft 提交的那一刻,这意味着超过一半的参与者拥有复制的日志。但可能有一部分参与者没有最新的日志,或者他们有日志但没有收到提交这些日志的指令。

或者 Raft 的读取线性化是否需要读取法定人数?

好吧,线性化适用于读取和写入,是的,两者都是通过法定人数完成的。为了使读取可线性化,读取必须由领导者处理,并且领导者必须验证它没有被更新的领导者取代将读取应用到状态机之后但在响应之前客户。但是,在实践中,许多 real-world 实现使用宽松的一致性模型进行读取,例如允许从追随者那里读取。但请注意,虽然 quorums 保证了 Raft 集群的线性化,但这并不意味着客户端请求是线性化的。要将线性化扩展到客户端,必须添加会话以防止 dropped/duplicated 客户端请求在 Raft 日志中为单个提交生成多个提交,这将违反线性化。

kuujo 已经解释了什么是线性化。我会在问题中回答你的其他问题。

But there may be a portion of the participants that don't have the latest logs or that they have the logs but haven't received instructions to commit those logs.

在领导者提交日志条目后,这可能是可能的,并且一些对等点现在没有这个日志条目,但其他对等点最终会以某种方式拥有它, Raft 做了几件事来保证:

  • 即使领导者已经提交了一个日志条目(让我们说 LogEntry at index=8)并回答了客户端,后台例程仍在尝试同步 logEntry:8给其他同龄人。如果 RPC 失败,(有可能)
  • Raft 周期性地发送心跳(一种AppendEntries),如果follower 没有,这个心跳RPC 会同步leader 有的日志给follower。在 followers 有 logEntry:8 之后,followers 将比较其本地的 commitIndex 和 RPC args 中的 leaderCommitIndex 来决定是否应该提交 logEntry:8。如果领导者在提交日志后立即失败,(这种情况很少见,但有可能)
  • Based on the election rule, only the one who has the logEntry:8 can win the election.选出新的 leader 后,新的 leader 会继续使用 heartBeat 同步 logEntry:8 到其他 peer。如果跟随者落后太多以至于无法从领导者那里获取所有日志,会发生什么情况? (当您尝试添加新节点时经常会发生这种情况)。在这种场景下,Raft 将使用快照 RPC 机制来同步所有数据和修剪后的日志。