第15章 复制

比较SYNC全量同步与PSYNC部分重同步,连接运行ID、复制偏移量、积压缓冲区和心跳 覆盖8个正式节点,并以Redis 3.0源码、故障和恢复对账验收。

学习目标

  • 能说明全量与增量同步的流程
  • 能解释 PSYNC 断线续传的判定
  • 能说明从库只读与读写分离

为什么从“PSYNC偏移与积压缓冲台”开始

第15章 复制的核心任务是比较SYNC全量同步与PSYNC部分重同步,连接运行ID、复制偏移量、积压缓冲区和心跳。命令返回值只暴露外层合同;实现解释还必须连接内存结构、写入与读取路径、事件顺序以及失败后的旧状态回收。PSYNC偏移与积压缓冲台把这些关系放进同一条可复位轨迹。

先写预测:当断线跨度由“仍在backlog”进入“超出backlog”时,哪个可观察状态最先变化?再规定什么结果会推翻当前解释。交互中的分数只表达透明因果方向,不冒充真实Redis测量。

来源、版次与独立重写边界

黄健宏作者读者服务页确认正式出版新版以Redis 3.0为源码基线,列出4部分、24章及完整小节,并链接Redis 3.0中文注释源码。本课程据此映射24个正式单元、145个目录节点,另设学习地图和总复习;未取得出版正文授权,目录只界定范围,不宣称复现原书正文。

本章字段与控制流由Redis官方3.0源码:replication.c和作者注释源码交叉核对;Redis当前持久化文档只用于辨认版本差异。中文解释、图示、交互、实验与答案均为独立教学重写,不把目录页或代码仓库许可证误报为原书许可证。

本章术语与源码合同

第15章 复制必须守住“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”。观察同时记录PSYNC偏移与积压缓冲台一致率与身份条件分叉风险;只有结构快照、函数入口、运行结果和故障反例互相一致,才接受实现结论。

⚡ 主从复制与同步流程
主从复制(当前阶段:握手连接正常MasterBGSAVE / 传播命令Slave同步执行命令1握手2全量同步3追增量4命令传播repl-backlog = 500 字节(PSYNC 部分同步的覆盖窗口)
全量同步打底、命令传播保一致、PSYNC 用 offset 判断能否部分同步。repl-backlog 太小会退化为全量重传;从库默认只读防止数据分叉。主库侧写命令会进入积压缓冲区以支撑断线续传。
操作日志
  1. 1.复制:全量同步(RDB)+ 命令传播(增量)+ PSYNC 断线续传。

作者目录逐项深读

旧版复制功能的实现

四级证据 1/8。 SYNC要求主节点BGSAVE并传输完整RDB,随后传播缓冲期写命令;断线后通常再次全量同步。本节点用“旧版复制功能的实现”作观察点,执行rg 'syncCommand|masterTryPartialResynchronization|replicationFeedSlaves' src/replication.c或等价源码探针,保存版本、输入、前后状态和能推翻解释的反例。

验证旧版复制功能的实现时,先预测断线跨度从“仍在backlog”切到“超出backlog”会改变哪个字段、偏移、文件或消息;再固定身份条件做一次对照。若故障注入没有破坏“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,就撤回当前解释而不是补写故事。

旧版复制功能的缺陷

四级证据 2/8。 短暂断线也全量复制会重复fork、磁盘与网络成本,并放大主从重新可用时间。本节点用“旧版复制功能的缺陷”作观察点,执行rg 'syncCommand|masterTryPartialResynchronization|replicationFeedSlaves' src/replication.c或等价源码探针,保存版本、输入、前后状态和能推翻解释的反例。

验证旧版复制功能的缺陷时,先预测断线跨度从“仍在backlog”切到“超出backlog”会改变哪个字段、偏移、文件或消息;再固定身份条件做一次对照。若故障注入没有破坏“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,就撤回当前解释而不是补写故事。

新版复制功能的实现

四级证据 3/8。 PSYNC以runid和offset判断能否继续,无法匹配时才退回完整同步。本节点用“新版复制功能的实现”作观察点,执行rg 'syncCommand|masterTryPartialResynchronization|replicationFeedSlaves' src/replication.c或等价源码探针,保存版本、输入、前后状态和能推翻解释的反例。

验证新版复制功能的实现时,先预测断线跨度从“仍在backlog”切到“超出backlog”会改变哪个字段、偏移、文件或消息;再固定身份条件做一次对照。若故障注入没有破坏“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,就撤回当前解释而不是补写故事。

部分重同步的实现

四级证据 4/8。 主节点在固定大小backlog保留最近复制字节;请求偏移仍在窗口内且runid匹配时发送缺口。本节点用“部分重同步的实现”作观察点,执行rg 'syncCommand|masterTryPartialResynchronization|replicationFeedSlaves' src/replication.c或等价源码探针,保存版本、输入、前后状态和能推翻解释的反例。

验证部分重同步的实现时,先预测断线跨度从“仍在backlog”切到“超出backlog”会改变哪个字段、偏移、文件或消息;再固定身份条件做一次对照。若故障注入没有破坏“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,就撤回当前解释而不是补写故事。

PSYNC命令的实现

四级证据 5/8。 副本发送已知runid与下一偏移,主节点返回CONTINUE或FULLRESYNC并给出新的身份与偏移。本节点用“PSYNC命令的实现”作观察点,执行rg 'syncCommand|masterTryPartialResynchronization|replicationFeedSlaves' src/replication.c或等价源码探针,保存版本、输入、前后状态和能推翻解释的反例。

验证PSYNC命令的实现时,先预测断线跨度从“仍在backlog”切到“超出backlog”会改变哪个字段、偏移、文件或消息;再固定身份条件做一次对照。若故障注入没有破坏“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,就撤回当前解释而不是补写故事。

复制的实现

四级证据 6/8。 完整同步后主节点持续把写命令传播给副本,双方用复制偏移记录字节流进度。本节点用“复制的实现”作观察点,执行rg 'syncCommand|masterTryPartialResynchronization|replicationFeedSlaves' src/replication.c或等价源码探针,保存版本、输入、前后状态和能推翻解释的反例。

验证复制的实现时,先预测断线跨度从“仍在backlog”切到“超出backlog”会改变哪个字段、偏移、文件或消息;再固定身份条件做一次对照。若故障注入没有破坏“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,就撤回当前解释而不是补写故事。

心跳检测

四级证据 7/8。 副本周期发送REPLCONF ACK偏移,主节点据此观察连接存活、复制滞后并支持min-slaves约束。本节点用“旧版复制功能的实现”作观察点,执行rg 'syncCommand|masterTryPartialResynchronization|replicationFeedSlaves' src/replication.c或等价源码探针,保存版本、输入、前后状态和能推翻解释的反例。

验证心跳检测时,先预测断线跨度从“仍在backlog”切到“超出backlog”会改变哪个字段、偏移、文件或消息;再固定身份条件做一次对照。若故障注入没有破坏“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,就撤回当前解释而不是补写故事。

重点回顾

四级证据 8/8。 第15章 复制的回顾要重新证明“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,并用同一输入比较结构前态、变更轨迹、故障首错与恢复后态

验证重点回顾时,先预测断线跨度从“仍在backlog”切到“超出backlog”会改变哪个字段、偏移、文件或消息;再固定身份条件做一次对照。若故障注入没有破坏“主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉”,就撤回当前解释而不是补写故事。

最小源码与运行切片

+git clone --branch 3.0 --depth 1 https://github.com/redis/redis.git redis-3.0
+cd redis-3.0
+rg 'syncCommand|masterTryPartialResynchronization|replicationFeedSlaves' src/replication.c

该切片固定Redis 3.0分支、编译器、配置、数据集和命令序列;先保存结构或函数位置,再运行隔离实例。任何持久化损坏、断线、故障转移、大键或高流量实验都必须使用临时数据并规定CPU、内存、磁盘、延迟和停止上限。

unit: rdi-15-replication
source_file: replication.c
axis_a: "断线跨度"
axis_b: "身份条件"
fault: "在runid或偏移不连续时仍做部分重同步,使副本静默分叉"
invariant: "主从偏移与数据一致,断线重连正确选择全量或部分同步,命令传播顺序不分叉"
replay: same_version_same_input

三个必须主动触发的误区

误区 1

现象 → 积压缓冲区默认太小 原因 → 断线即全量重传 修法 → 按写入速率调大 repl-backlog

误区 2

现象 → 主从网络不管控 原因 → 复制延迟悄悄放大 修法 → 监控复制延迟并设告警

误区 3

现象 → 从库挂主库下 原因 → 旧数据服务新请求 修法 → 配 min-replicas 保护写入

小结

  • 主从复制以全量加增量同步
  • PSYNC 优化断线重连
  • 复制积压缓冲区支撑部分同步
  • 从库只读避免写分叉
  • 心跳与延迟监控不可少

练习、答案与节点验证

练习

问题 1: PSYNC 如何避免断线后的全量重传?

问题 2: 为什么从库默认只读?

问题 3: 估算 10GB 数据全量重传的代价并给出规避方案。(独立实现)

术语复核与本章回顾

完成第15章 复制意味着能从replication.c解释比较SYNC全量同步与PSYNC部分重同步,连接运行ID、复制偏移量、积压缓冲区和心跳,能运行章专属状态实验,能制造反例并在复位后证明旧状态没有残留。

资料与写作方式声明

本章以黄健宏《Redis设计与实现》(机械工业出版社)权威目录界定学习范围,并结合正文列出的技术资料独立重写;不宣称复现原书正文,也不沿用原作表述。

原作版权归作者与出版社所有;本站原创教学结构与表述仅供学习交流。

讨论

评论区加载中…