Raft日志复制

快速理解Raft之日志复制(肝了两千五百字) Raft的日志复制,常见冲突以及对应的冲突解决方案。 阅读详情

Raft中的Log Entry包括以下内容
索引 Index 记录该日志条目在整个日志中的位置
任期号 Term 日志条目首次被领导者创建时的任期
命令 应用于状态机的命令

日志复制

Raft算法通过索引和任期号唯一标识一条日志记录

日志必须持久化存储,一个节点必须先把日志条目安全写入到磁盘中,才能向系统其他节点发送请求或回复请求。
如果一条日志条目被存储到超过半数节点上,则认为该记录已提交(committed)。如果一条记录已提交,状态机可以安全地执行该记录,这条记录就不能再改变了。
如图,第1条到第7条日志已提交,第8条未提交。
提交日志
Raft通过AppendEntries消息复制日志,与心跳消息共用同一个RPC,不过用于心跳时不附加日志信息。
Raft算法正常运行时,日志复制流程为:
(1) 客户端向领导者发送命令
(2) 领导者先将命令追加到自己的日志中,确保日志持久化存储
(3) 领导者向其他节点发送AppendEntries消息,等待相应
(4) 如果收到超过半数节点响应,则认为新的日志记录已提交。接着领导者将命令应用(apply)到自己的状态机,然后向客户端返回响应。此外,一旦领导者提交了一个日志记录,将在后续的AppendEntries消息中通过LeaderCommit参数通知跟随者,告知领导者已提交的最大日志索引,跟随者也提交索引小于LeaderCommit的日志,并将命令应用到自己的状态机。
(5) 如果跟随者宕机或请求超时,日志没有复制成功,那么领导者将反复尝试发送AppendEntries消息。
(6) 性能优化:领导者不必等待所有跟随者做出响应,只要半数的跟随者成功响应(日志已经存储到超过半数的节点上)就可以回复客户端了。这样保证即使存在一个很慢的或故障节点,也不会成为系统的瓶颈。

Raft算法的日志通过索引和任期号唯一表示一个日志条目,为了保证安全性,Raft维持以下两个特性:
(1) 如果两个节点的日志在相同的索引位置上的任期号相同,则认为它们具有一样的命令,并且从日志开头到这个索引位置之间的日志也完全相同。
(2) 如果给定的日志已提交,那么之前所有的日志都已提交 .
在这里插入图片描述

一致性保证

Raft通过AppendEntries消息来检测之前的一个日志条目,每个AppendEntries请求包含新的日志条目之前的一个日志条目的索引和任期(记为prevLogIndex和prevLogTerm),追随者收到请求后,会检查自己最后一条日志的索引和任期号是否与请求消息中的prevLogIndex和prevLogTerm相同,相同则接收记录,否则拒绝。
可以通过数学归纳法证明以上方式能保证AppendEntries消息之前的日志都是相同的。

代码框架

package go_raft

type LogEntry struct {
	Index   int
	Term    int
	Command interface{}
}

type AppendEntriesArgs struct {
	Term         int
	LeaderId     int
	PrevLogIndex int
	PrevLogTerm  int
	//需要复制的日志条目,发送心跳时为空
	Entries []LogEntry
	//领导者已提交最大日志索引,用于跟随着提交
	LeaderCommit int
}

type AppendEntriesReply struct {
	Term    int
	Success bool
}

func (rf *Raft) AppendEntries(args *AppendEntriesArgs, reply *AppendEntriesReply) {
	rf.mu.Lock()
	defer rf.mu.Unlock()

	reply.Term = rf.currentTerm
	reply.Success = false
	if args.Term < rf.currentTerm {
		return
	}

	if args.Term > rf.currentTerm {
		reply.Term = args.Term
		rf.currentTerm = args.Term
	}

	//重置选举超时时间
	rf.setState(Follower)

	//日志一致性检查
	lastLogIndex := len(rf.log) - 1
	if args.PrevLogIndex > rf.log[lastLogIndex].Index || rf.log[args.PrevLogIndex].Term != args.PrevLogTerm {
		return
	}

	reply.Success = true

	//处理重复的RPC请求
	//比较日志条目的任期,以确认是否能够安全地追加日志
	//否则会导致重复应用命令
	index := args.PrevLogIndex
	for i, entry := range args.Entries {
		index++
		if index < len(rf.log) {
			if rf.log[index].Term == entry.Term {
				continue
			}
			rf.log = rf.log[:index]
		}

		rf.log = append(rf.log, args.Entries[i:]...)
		break
	}

	if rf.commitIndex < args.LeaderCommit {
		lastLogIndex = rf.log[len(rf.log)-1].Index
		if args.LeaderCommit > lastLogIndex {
			rf.commitIndex = lastLogIndex
		} else {
			rf.commitIndex = args.LeaderCommit
		}
		//将命令应用到自己的状态机
		rf.apply()
	}

	//保险起见,再重置一次选举超时时间
	rf.setState(Follower)
	return
}

Raft协议详解(三)日志复制 在这一部分,我们讲Raft几个子问题中的日志复制问题。主要内容是讲Raft为什么要进行日志复制,以及如何进行日志复制的。日志复制(log replication)是leader的主要工作之一。在前面的第一、二部分,我们讲到了日志(log)是Raft的一致性保证非常重要的组成部分,很大程度Raft是利用log做的数据一致性。那么我们就来说说日志。 日志是啥 上图是Raft论文中的图片... 阅读详情

相关推荐

Raft 实现日志复制同步

Raft 实现日志复制同步 本篇文章以 John Ousterhout(斯坦福大学教授) 和 Diego Ongaro(斯坦福大学获得博士学位,Raft算法发明人) 在 Youtube 上的讲解视频及 ppt 为蓝本,深入分析 Raft 的内部机制,并以日志复制同步(Replicated Logs)为背景,详细介绍使用 Raft 协议实现日志复制的共识性问题。 目标:日志复制同步 R

平夫博客 1293

Raft算法之日志复制

在Leader选举过程中,集群最终会选举出一个Leader节点,而集群中剩余的其他节点将会成为Follower节点。Leader节点除了向Follower节点发送心跳消息,还会处理客户端的请求,并将客户端的更新操作以消息(Append Entries消息)的形式发送到集群中所有的Follower节点。当Follower节点记录收到的这些消息之后,会向Leader节点返回相应的响应消息。当Leader节点在收到半数以上的Follower节点的响应消息之后,会对客户端的请求进行应答。

一直在努力的小渣渣 2285

Raft算法日志复制与选主机制源码分析

Raft算法的选主机制是其高可用性和一致性的重要保障,通过选举过程确保集群中始终有一个领导者节点来协调日志复制和其他操作。选举状态:每个节点在Raft算法中可以处于三种状态之一:跟随者、候选人或领导者。跟随者节点负责接收领导者的指令并执行;候选人节点在选举过程中尝试成为领导者;领导者节点负责协调日志复制和处理客户端请求。在正常运行时,大多数节点处于跟随者状态,只有当跟随者在超时时间内未收到领导者的心跳消息时,才会转变为候选人并发起选举。选举超时。

qq_40552871的博客 785

Raft协议--日志复制--03

一、日志复制的过程 客户端的一条指令到达,Leader把将指令作为日志条目(Log entries)加入到它的日志中,然后并行的向其他Follower发起 AppendEntries(附加条目) RPC复制日志条目。当这条日志被复制到大多数服务器上,Leader将这条日志应用到它的状态机(比如如果是mysql的insert,那么就是执行insert操作),并向客户端返回执行结果。 客户端的每一个请求都包含被复制状态机执行的指令。 leader把这个指令作为一条新的日志条目添加到日志中,然后并行发起

zhou920786312的博客 1370

告别MRT!用ArcGIS脚本批量处理MODIS数据,从HDF到NDVI/ET成品图全流程(附Python代码)

本文详细介绍了使用ArcGIS Python脚本自动化处理MODIS数据的全流程,从HDF文件提取到生成NDVI/ET成品图。通过优化子数据集提取、智能镶嵌策略和投影转换等核心步骤,大幅提升处理效率,告别传统MRT工具的手工操作。附带的Python代码可直接应用于实际项目,特别适合批量处理大规模遥感数据。

weixin_30872337的博客 219

人工智能情感分析实战:文本情绪识别

人工智能情感分析,特别是文本情绪识别,已成为理解和处理人类情感信息的重要工具。通过数据预处理、特征提取、模型训练与评估等步骤,我们可以有效地从文本数据中提取情感信息,为各种应用场景提供有价值的洞察。随着技术的不断进步和创新,情感分析的应用前景将更加广阔,为我们的生活和工作带来更多便利和机遇。

shejizuopin的博客 1095

超详细教程!手把手带你使用Raft分布式共识性算法

导语|从头理一遍Raft会给你带来新的体验与收获,让你从根本上理解Raft,理解它被提出的背景,在此背景下又是如何解决实际问题的,这才是从头实现一个Raft所带来的真正收益。本文聚焦在R...

QcloudCommunity的博客 1693

人形机器人系列——硬件介绍

人形机器人是多领域交叉技术的产物,主要由三大系统组成:感知系统、决策系统和执行系统。感知系统感知系统是人形机器人获取外界信息的途径,主要由各种传感器组成。其中,视觉传感器用于获取图像信息,如摄像头、激光雷达等;触觉传感器用于感知触碰和压力,如力/力矩传感器、声学传感器等。这些传感器收集到的信息为机器人的决策和执行提供基础。决策系统决策系统是人形机器人的大脑,负责处理和决策各种信息。它由芯片和算法组成。芯片是硬件基础,提供计算能力;算法是软件基础,用于处理和分析传感器收集到的信息,并做出相应的决策。执行系统。

liangwqi的博客 1万+

08 | Raft算法(二):如何复制日志?

通过上一讲的学习,你应该知道 Raft 除了能实现一系列值的共识之外,还能实现各节点日志的一致,不过你也许会有这样的疑惑:“什么是日志呢?它和我的业务数据有什么关系呢?想象一下,一个木筏(Raft)是由多根整齐一致的原木(Log)组成的,而原木又是由木质材料组成,所以你可以认为日志是由多条日志项(Log entry)组成的,如果把日志比喻成原木,那么日志项就是木质材料。

qq_37756660的博客 1406

Claude Code与Vibe Coding:2026年AI编程实战指南

AI编程助手是基于大语言模型的智能代码生成工具,通过理解编程上下文提供精准的代码补全和重构建议。其核心原理是利用深度学习技术分析代码语义,将自然语言指令转化为可执行代码。这种技术能显著提升开发效率,减少重复性编码工作,特别适用于快速原型开发和复杂问题求解。在实际应用场景中,AI编程助手可与Vibe Coding方法论结合,建立流畅的人机协作工作流。Claude Code作为先进的AI编程工具,支持多语言开发和智能错误检测,而Vibe Coding则强调自然交互和迭代优化,两者协同为开发者提供完整的AI编程解

weixin_29057695的博客 341

主动式桥梁防船撞预警系统的方案汇总

本系统以精密光电测高前端(2台,上下游各1台)、固态雷达(2台,上下游各1台)、AIS(1台)、偏航辅助前端(4台,上下游各2台)为核心,通过人工智能,对画面上的船舶目标进行深度学习、精确定位,再用系统集成方法将各设备有机结合在一起,构建成套的桥梁防撞主动预警系统,全天候监控过往船舶。主动式桥梁防船撞预警系统主要船舶监测采集单元、控制单元、船舶超高、偏航信息检测单元、以及视频监控单元组成,,通过声光警示、短信文字、船舶身份识别及海事对讲频道、视频录像取证等多种手段与船舶进行信息互动,主动防止船舶碰撞桥梁!

gdxixun的博客 972

Raft 日志复制

Raft 日志复制的目标是让所有副本维护一致、有序的日志副本。它通过 AppendEntries、任期与索引校验、日志回退与快照恢复等机制,在保证一致性的同时提供高性能、高可靠的副本同步能力。Leader 选举机制快照发送的详细过程如何避免脑裂Raft 与 Paxos 的对比。

喝醉酒的小白 822

开源DIY龙门架:从零构建可编程运动控制平台

运动控制是自动化与机器人技术的核心基础,它通过精确指令驱动执行机构,实现物体的定位与轨迹规划。其原理通常涉及控制器、驱动器、电机与传动机构的协同工作,核心价值在于将数字指令转化为精准的物理运动,从而解放人力并提升作业一致性。在工业自动化、桌面制造(如3D打印、激光雕刻)及教育机器人等领域应用广泛。本文聚焦于一个具体的工程实践案例:使用**铝型材**、**3D打印**零件、Arduino控制器及步进电机,从机械结构设计、电路连接到代码编写,手把手教你打造一个模块化、可扩展的开源龙门架系统。该系统不仅成本可控,

weixin_33168937的博客 616

Raft 算法详解(二)日志复制

在 Raft 算法中,副本数据是以日志的形式存在的,领导者接收到来自客户端写请求后,处 理写请求的过程就是一个复制和提交日志项的过程。 那 Raft 是如何复制日志的呢?又如何实现日志的一致的呢?这些内容是 Raft 中非常核心 的内容,首先,咱 们先来理解日志,这是你掌握如何复制日志、实现日志一致的基础。 如何理解日志? 刚刚我提到,副本数据是以日志的形式存在的,日志是由日志项组成,日志项究竟是什么样 子呢? 其实,日志项是一种数据格式,它主要包含用户指定的数据,也就是指令(Command), 还包含一些

林木森的博客 2413

SAP在sap我定义了三个帐套 T9 SGD,I9 CNY, C9 CMY 想使用三个不同的币种,那么 我在定义和激活非主分类账时 如何定义各自的币种 ?

摘要:在SAP中为非主分类账(T9、I9、C9)配置不同币种(SGD、CNY、MYR),需通过三个步骤实现:1)在FINSC_LEDGER中定义分类账货币类型;2)在OB22中为公司代码0919配置平行货币;3)在"定义和激活非主分类账"中关联币种。关键注意事项包括维护自定义货币类型(以Y/Z开头)、设置OB08汇率以及独立汇率评估。完成后可通过FB50测试凭证和FAGLL03验证各账套的币种金额显示。

金牌架构师 1012

Unity中使用TCP和UDP传输摄像头视频的实践

本文探讨了在Unity中通过TCP和UDP协议传输摄像头视频的实现方法。TCP通过自定义消息帧保证数据完整性但效率较低,UDP传输速度快但可能丢帧。文章提供了Python和Unity的代码示例,分析了两种协议的适用场景:TCP适合要求数据完整性的应用,UDP则适合追求实时性的场景。最终选择取决于具体需求,并需要注意线程安全与同步机制。

m0_74337424的博客 145

Raft日志复制技术及成员变更原来是这样的

副本数据是以日志的形式存在的,日志是由日志项组成,日志项究竟是什么样子呢?其实,日志项是一种数据格式,它主要包含用户指定的数据,也就是指令(Commond),还包含一些附加信息,比如索引值(Log Index)、任期编号(Term)。指令:一条由客户端请求指定的、状态机需要执行的指令。可以将指令理解成客户端指定的数据。索引值:日志项对应的整数索引值,其实就是用来标识日志项的,是一个连续的、递增的整数号码。任期编号:创建这条日志项的领导者的任期编号。

我是一名热爱编程和分享知识的技术作者,在金融和教育领域有多年的研发管理经验,感谢您访问我的博客,一定会为您带来不一样的收货! 1718

VB摄像头监控

该VB模块可对摄像头捕获的画面进行录像等,可在创建的窗口进行控制

Raft 共识算法学习笔记 二:日志复制

文章 Raft 共识算法学习笔记 一:领导人选举 描述了 Raft 算法如何进行领导者选举,本文描述 Raft 共识算法如何进行日志复制。 复制状态机 在 Raft 集群中,每个服务器可以看成是一个复制状态机(Replicated State Machine),如下图。 复制状态机通常基于复制日志(replicated log)实现。每个服务器存储一个包含一系列指令的日志,并且按顺序执行指令。由于日志都包含相同顺序的指令,状态机会按照相同的顺序执行指令,由于状态机是确定的(deterministic),因此

Leo的博客 1689

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

TMS_WebGMaps_1.9.8.0_Full_Source

TMS_WebGMaps_1.9.8.0_Full_Source 全源码 delphi cbuilder

C++实现Raft算法之日志复制

基于Raft的kv存储之日志复制部分

weixin_45962681的博客 1173

OV9734 DATASHEET,完整规格书

OV9734完整规格书,包括电气参数,尺寸规格,寄存器配置表等

图解Raft之日志复制

日志复制可以说是Raft集群的核心之一,保证了Raft数据的一致性,下面通过几张图片介绍Raft集群中日志复制的逻辑与流程;   在一个Raft集群中只有Leader节点能够接受客户端的请求,由Leader向其他Follower转发所有请求日志,并且有那么两条规则:Leader不删除任何日志、Follower只接收Leader所发送的日志信息;   此图介绍了Raft集群中日志的组成结构,日志...

weixin_30699443的博客 1402

【Raft原理探究·日志复制详解】老大带头抄作业

Raft 是一套为理解和实现分布式一致性而设计的共识算法,本文通过类比开发团队“组长带队干活”的形象方式,深入浅出地讲解了 Raft 中日志复制的完整过程。包括从 Leader 写入日志、同步 Followers、副本确认、提交执行、补日志对齐等环节,并结合两阶段提交机制解析其强一致性保障。适合有一定基础的工程师查漏补缺,也适合初学者建立系统理解。

PragueJoker的博客 1054

Raft 共识算法3-日志复制

为了使跟随者的日志与其自己的一致,领导者必须找到在跟随者的日志中和自己一致的最新日志条目,然后在跟随者日志中删除该点之后的所有条目,并将该点之后的所有领导者日志条目发送给跟随者。当发生这种情况时,AppendEntries RPC 将成功,它会删除跟随者日志中的所有冲突条目并追加领导者日志中的条目(如果有的话)。一旦创建条目的领导者已将其复制到大多数服务器(例如,@fig6 中的条目 7),那么该日志就被称为已提交的(此时将该日志条目应用到状态机是安全的)。日志是由条目组成的,这些条目按顺序编号。

serene的博客 620

Raft算法的Leader选举和日志复制过程

Raft概念 Raft是一种为了管理复制日志的一致性算法。它提供了和Paxos算法相同的功能和性能,但是它的算法结构和Paxos不同,使得Raft算法更加容易理解并且更容易构建实际的系统。为了提升可理解性,Raft将一致性算法分解成了几个关键模块,例如Leader选举、日志复制和安全性。同时它通过实施一个更强的一致性来减少需要考虑的状态的数量。从一个用户研究的结果可以证明,对于学生而言,Ra...

Tyler_Zx的博客 1万+
上一篇: Raft 领导者选举
下一篇: Raft领导者变更的安全性
yumWant2debug
博客等级 码龄7年 27粉丝 26原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值