分布式快照、MVCC 与混合逻辑时钟

05-事务与数据系统 进阶 约 20 分钟 #快照#MVCC#HLC#一致性读 更新 2026-10-02
当前状态:未学
本文基于模型知识整理(生成时未联网核对),关键结论建议对照经典文献复核。

一句话定义

分布式系统需要"某个全局时刻的完整一致视图"来做备份、一致性读与事务排序:Chandy-Lamport 快照协议在不停止系统的情况下抓取一致性切面,MVCC 用多版本让读者不阻塞写者,混合逻辑时钟(HLC)则给"无专用时钟硬件"的系统提供接近物理时间的因果时间戳。

为什么重要

"备份时数据在变怎么办""隔离级别底层怎么实现""跨地域数据库的时间戳从哪来"——三个高频工程问题的答案都指向本条。它是连接一致性模型(kp-013)与存储引擎实现(kp-032)的桥梁层。

前置知识

kp-004(逻辑时钟)、kp-023(提交语义)。

核心概念

  • 一致性快照(consistent snapshot):快照内部满足"如果记录了某消息的接收,也必记录其发送"——即不出现"凭空出现的消息"。
  • Chandy-Lamport 协议: initiator 发带标记(marker)的记录消息;节点收到首个 marker 时记录自身状态并把自己的出边全部打标;marker 在信道上的语义是"此前收到的都算入快照"。系统不停机,快照异步完成。
  • MVCC(多版本并发控制):每次写产生新版本(带版本号/时间戳),读按快照版本取可见版本——读写互不阻塞,是快照隔离与一致性读的引擎。
  • HLC(Hybrid Logical Clock):时间戳 = (物理毫秒, 逻辑计数),物理部分跟随本地墙钟并与所见消息取最大,逻辑部分在物理部分不变时递增——既接近真实时间(便于 TTL/调试/分页),又保持因果单调(物理时钟回拨也能保证递增)。

原理与机制

为什么快照协议能保证一致性:marker 划定了每条信道的"分界线"——分界前收到的消息,其发送必然发生在发送方记录状态之前(消息先行于 marker)。归纳起来快照里不存在"接收在快照内、发送在快照外"的幻影消息,于是快照是系统的一个可达状态(可作恢复点)。注意它记录的是切面状态而非"某一物理瞬间"——异步系统本没有全局瞬间。

MVCC 与隔离级别的映射:只读最新已提交版本 = 读已提交;读"事务开始时"的版本 = 快照隔离;可见性判定再叠加提交时间戳排序 = 可串行化的基础(SSI 在其上加冲突检测)。存储层实现通常是 per-key 版本链 + GC(老版本回收,回收水位依赖活跃事务最小快照点——长事务会顶住 GC 水位,是 MVCC 系统的经典运维坑)。

HLC 解决什么:纯逻辑时钟(kp-004)与真实时间脱节(TTL、按时间查询困难);纯物理时钟不单调(kp-003)。HLC 以物理时间为主轴、逻辑计数兜底因果,让单库时间戳可直接跨库比较(CockroachDB 用它做全局事务时间戳,无需 TrueTime 硬件)。

图示

Chandy-Lamport:
 P1 ──[marker]──► P2: P2 收到 marker → 记录自己状态 → 对 P2 的出边打标
 信道语义: marker 之前收到的消息已入快照, 其发送方必已记录 → 无幻影消息

MVCC:
 key=balance: v5=100(ts=41) ← v6=80(ts=47) ← v7=95(ts=52)
 事务(快照ts=47)读 balance → 取 ts≤47 的最新版本 v6=80

实例或案例

  • 数据库在线备份:基于 MVCC 快照的一致性备份(如 TiDB BR、PG pg_backup_start 时代的备份)无需停写。
  • Kafka Streams / Flink 的 checkpoint:分布式快照思想(barrier 对齐)实现 Exactly-once 状态。
  • CockroachDB:HLC 时间戳 + MVCC 版本链,跨地域无硬件获得可串行化事务。
  • TiDB:中心化 TSO(单一时间戳服务)发号 + Percolator 风格 MVCC,另一种时间戳来源路线。

常见误区

  • 误区一:"快照 = 某一物理时刻的冻结"。异步系统无全局瞬间;快照是一致性切面(因果自洽的状态),两组件的记录时刻可以不同。
  • 误区二:"MVCC 无锁所以没有代价"。写写冲突仍需检测/等待;长事务阻止版本 GC,历史版本膨胀会拖垮读性能与磁盘。
  • 误区三:"HLC 让墙钟变准了"。HLC 不修正物理时钟(kp-003 的结论不变),只是把"物理部分"包进单调因果框架,物理部分本身仍不可信。

与其他知识点的关系

  • kp-003/004:HLC 是物理与逻辑时钟的合流点。
  • kp-013:MVCC 是一致性读的实现载体。
  • kp-023/032:跨节点提交的时间戳排序(Spanner commit wait、TiDB TSO、CRDB HLC 三条路线对比)。

自测题

  1. Chandy-Lamport 快照如何排除"幻影消息"?

答:marker 划定信道分界,marker 前收到的消息其发送必在发送方快照记录之前(消息先于 marker 传播),故快照中消息的收发两端闭合。

  1. 为什么长事务会拖垮 MVCC 系统?

答:GC 水位取决于最老活跃事务的快照点,长事务使其后所有旧版本无法回收,版本链膨胀拖慢读与占用存储。

  1. HLC 相比纯 Lamport 时钟多了什么能力?

答:时间戳携带真实物理时间信息,支持 TTL、按时间范围查询与跨系统调试,同时保留因果单调性。

延伸阅读

  • K. Mani Chandy & Leslie Lamport, "Distributed Snapshots: Determining Global States of Distributed Systems"(TOCS 1985)。
  • CockroachDB 文档:HLC 设计(hybrid logical clock RFC)。
  • Kleppmann《DDIA》第 7 章(快照隔离与可串行化)。