读修复和反熵修复有什么区别?
简化版
读修复在一次读取发现副本版本不同时,顺便把旧副本更新;它及时覆盖热点数据,但冷数据无人读就不会修。 反熵由后台周期比较副本摘要或 Merkle Tree,主动定位并修复差异,能覆盖冷数据但消耗扫描、网络和 IO。 生产系统通常组合使用,并以版本/墓碑判断修复方向,不能看到不同就盲目覆盖。
详细版
读协调者向多个副本取版本,返回满足一致性级别的结果,再同步或异步写回落后副本。 同步修复增加读延迟,异步修复缩短请求时间但延长不一致窗口。
反熵按 token range/分区建立摘要,在共同稳定边界比较差异树,只传输不同范围。 墓碑在所有副本确认或超过安全宽限期前不能清除,否则已删除数据可能被旧副本复活。 监控修复字节、差异年龄、失败、积压和前台延迟影响。
完整版教学
一、两者触发方式不同
读修复由用户读取触发。 反熵由后台计划任务触发。 一个偏实时热点,一个偏完整覆盖。
读修复靠访问概率,反熵靠系统主动证明副本收敛。
二、读修复流程
read replicas A,B,C
-> compare version/value
-> choose or merge result
-> return according to consistency level
-> repair stale replicas
冲突值无法自动比较时,应返回 siblings 或按业务策略合并。
三、同步与异步读修复
同步等待修复完成再返回,缩短不一致但提高 P99。 异步先返回结果,后台写回,用户延迟低但任务可能失败。 常见做法是前台满足读取 quorum,修复异步且可重试。 高风险数据不能仅依赖“以后某次读会修”。
四、反熵流程
副本按相同分区和水位生成哈希树。 根不同则比较子节点,递归定位差异 key。
| 特性 | 读修复 | 反熵 |
|---|---|---|
| 触发 | 业务读 | 后台周期 |
| 覆盖 | 热点 | 全量/分区 |
| 延迟影响 | 可能影响读 | 消耗后台资源 |
| 冷数据 | 无法保证 | 可以修复 |
五、版本与冲突
修复必须用版本向量、HLC、业务 revision 或状态机判定新旧。 物理时间最大不一定正确。 并发版本需要合并或保留,不能随机选一个。 写回使用条件更新,防止修复过程中覆盖更新版本。
六、删除与墓碑
一个副本已删除,另一个离线仍有旧值。 若墓碑过早 GC,反熵会把旧值当合法数据复制回来。 墓碑保留时间要覆盖最长离线与修复周期。 永久离线节点重返集群前可能需要完整重建。
七、资源控制
反熵限速、分片、错峰,避免与业务 IO 争用。 节点恢复时设置并发和带宽预算。 监控 repair backlog、bytes、oldest divergence、成功率与读修复触发率。 频繁修复同一键说明写传播或冲突策略存在问题。
八、常见误区与追问
- 误区:有读修复就不需反熵。 冷数据可能永远无人读取。
- 误区:反熵全表逐行比较即可。 大规模系统应分区并用摘要下钻。
- 误区:版本不同就用时间戳大的覆盖。 并发与漂移需要更可靠规则。
- 误区:删除后立即清墓碑最省空间。 会导致旧值复活。
- 追问:同步读修复有何代价? 增加请求尾延迟。
- 追问:Merkle Tree 有何作用? 快速定位不同分支,减少数据传输。
- 追问:修复写如何防并发覆盖? 携带预期版本做条件更新。
九、加强记忆
- 读修复随访问,适合热点。
- 反熵主动扫描,覆盖冷数据。
- 版本规则决定修复方向。
- 并发版本要合并,墓碑防删除复活。
- 两者组合并限速观测,才能完成最终收敛。