CAP/Raft、CDC 与 Outbox

共 19 题
📑 题目列表 19 题
#
★★★

1. Saga 长事务模式,拆分 + 补偿?

Saga 长事务模式是什么?如何通过拆分 + 补偿实现分布式事务?

  • Saga 模式的概念
  • 拆分与补偿机制
  • Saga 的编排与协同方式

Saga 长事务模式是把一个大的分布式事务拆分成多个本地事务(子事务),每个子事务按顺序执行,并配套对应的补偿事务(compensation)。当某个子事务失败时,逆序执行已成功子事务的补偿事务,把系统回滚到初始状态,从而在"无全局锁、无两阶段提交"的情况下实现长事务的最终一致性。Saga 有两种编排方式:协同式(Choreography)——各服务通过事件相互触发,无中央协调者;编排式(Orchestration)——由中央协调器调用各子事务并管理补偿。Saga 适合跨服务、长执行、无需强一致性的业务(如订单、下单流程),但缺点是缺乏隔离性(中间状态可见)、补偿逻辑复杂。

Saga 的核心是"拆分 + 补偿":把大事务拆成分散的子事务,用补偿回滚。它放弃了 ACID 的隔离性,换取了长事务的可用性与最终一致性。相比 XA(两阶段提交),Saga 不占用全局锁、更灵活,但补偿的编写和正确性要求高。实际中常与 Outbox、消息可靠投递配合。

#
★★★

2. 分布式事务(Distributed Transaction)的必要性,跨库更新?

分布式事务(Distributed Transaction)的必要性是什么?跨库更新为何需要分布式事务?

  • 分布式事务的必要性
  • 跨库/跨服务更新的原子性
  • 分布式事务的权衡

分布式事务的必要性源于:当数据分布在不同数据库(分库分表)或不同服务(微服务)时,一次业务操作可能涉及对多个数据源的更新,这些更新必须作为一个整体原子提交(要么全部成功,要么全部失败),否则会出现部分成功导致的数据不一致。例如下单库存扣减 + 订单插入 + 账户扣款,若分散在不同库/服务,单机事务无法保证原子性,需要分布式事务。分布式事务的实现方案包括 XA(两阶段提交)、TCC、Saga、本地消息表 + MQ(最终一致)等,不同方案在"强一致/最终一致"与"性能/复杂度"之间取舍。

分布式事务是"跨库/跨服务操作原子性"的必然需求。其本质是扩展单机 ACID 到分布式环境。但强一致分布式事务(XA)成本和性能代价高,因此实践中常按业务选择最终一致(Saga、消息表)。是否使用分布式事务,取决于业务对原子性/一致性的要求。数据库未分片前单机事务即可满足,分片后才有此问题。

#
★★★

3. CAP 三角形中的约束冲突,CP(ZooKeeper、etcd)vs AP(DNS、Cassandra)?

CAP 三角形中的约束冲突是什么?CP(ZooKeeper、etcd)与 AP(DNS、Cassandra)系统如何取舍?

  • CAP 的三个属性
  • 一致性优先(CP)与可用性优先(AP)
  • 典型系统的取舍

CAP 定理指出分布式系统在发生分区(P)时,无法同时保证一致性(C)与可用性(A),只能二选一。CP 系统(如 ZooKeeper、etcd、TiDB、HBase)在分区时优先保证一致性,宁可拒绝请求(牺牲可用性)也不返回过期数据,多数派机制保证读到一致数据。AP 系统(如 DNS、Cassandra、Eureka)在分区时优先保证可用性,让服务继续响应,但可能返回过期或不一致的数据,靠最终一致收敛。Cassandra 默认是 AP(可调一致性,实际可在一致性级别上权衡),DNS 是 AP(最终一致)。理解 CP/AP 取舍,是选择分布式系统的基础。

CAP 的核心是"分区时 C 与 A 不可兼得"。CP 牺牲可用性保一致性(适合元数据、强一致场景),AP 牺牲一致性保可用性(适合高可用、可容忍最终一致的场景)。实际系统常提供可调一致性,在 C/A 间灵活权衡。ZooKeeper/etcd 用于选主和元数据(CP),Cassandra/DNS 用于高可用查询(AP)。

#
★★★

4. CAP 定理的精确表述,一致性、可用性、分区容忍性不可兼得?

CAP 定理的精确表述是什么?一致性、可用性、分区容忍性为何不可兼得?

  • CAP 定理的表述
  • 三个属性的含义
  • 分区时的取舍

CAP 定理(Brewer 定理)的精确表述:在分布式系统发生网络分区(Partition,P)时,无法同时保证一致性(Consistency,C)与可用性(Availability,A),只能三选二(实际上是分区时 C 与 A 二选一)。一致性指所有节点同一时刻看到相同数据;可用性指每个请求都能在合理时间内得到响应(非错误);分区容忍性指系统在节点间通信中断时仍能继续运行。因为网络分区是不可避免的(P 必须保证),所以分区发生时必须在 C 与 A 之间取舍:要么放弃一致性(返回可能过期的数据以服务请求,AP),要么放弃可用性(拒绝请求以保持一致性,CP)。

很多人误读为"C、A、P 三选二",其实 P 是必须面临的现实,关键是分区时在 C 与 A 间二选一。CAP 刻画了分布式系统的一个根本约束,而非可选的工程选择。理解 CAP 有助于在系统设计时明确优先一致性还是可用性,并选择相应的存储与协议(如 Raft/多数派是 CP 倾向,Cassandra 可调 AP)。

#
★★★

5. Paxos 与 Raft 的差异?

Paxos 与 Raft 的差异是什么?为何 Raft 更易实现?

  • Paxos 的角色与流程
  • Raft 的角色与流程
  • 两者工程差异

Paxos 与 Raft 都是基于多数派的一致性算法。Paxos 更抽象,角色包括 Proposer(提议者)、Acceptor(接受者)、Learner(学习者),通过多轮 Prepare/Accept 阶段在多数派上达成值一致,没有显式 Leader,且要处理多提议者竞争,实现复杂、难理解。Raft 把共识分解为三个模块:Leader 选举(任期 + 随机超时选唯一 Leader)、日志复制(Leader 把日志复制到多数派并提交)、安全性(只允许有最新日志的节点当选、Leader 只追加不覆盖)。Raft 显式化 Leader、日志按序、更易理解和实现,因此 etcd、Consul、TiKV 等广泛采用。两者在数据一致性保证上等价,工程复杂性上 Raft 更优。

两者的根本差异是"抽象程度与工程化"。Paxos 理论更通用但难落地,Raft 通过显式 Leader 和模块化把共识做工程化。就实用性而言,Raft 是当前主流。理解两者的共同核心(多数派决议)与差异(Leader 显式化、日志复制方式)是理解分布式共识的基础。

#
★★★

6. Raft 一致性算法的角色,Leader、Follower、Candidate?

Raft 一致性算法的角色有哪些?Leader、Follower、Candidate 分别如何工作?

  • Raft 的三角色
  • Leader 的职责
  • 选举过程与角色转换

Raft 中节点有三种角色:Leader(领导者)——负责接收客户端请求、把日志复制到 Follower、协调提交,是唯一能处理写请求的角色;Follower(跟随者)——被动响应 Leader 的日志复制和心跳,是最常见的状态;Candidate(候选者)——Follower 在选举超时后转换为 Candidate,发起选举请求自己成为 Leader。角色转换流程:初始所有节点为 Follower,选举超时后成为 Candidate 并投票,获得多数派投票的 Candidate 成为 Leader;Leader 通过心跳维持权威,若 Leader 失联,Follower 超时后重新进入选举。所有角色通过任期(term)和投票(随机超时)保证任意任期只有一个 Leader。

Raft 的三角色是它的核心抽象。Leader 承担写处理和日志复制,Follower 被动跟随,Candidate 是选举中间态。角色转换靠"任期 + 随机超时 + 多数派投票"保证选举安全。理解角色职责与转换,是理解 Raft 选举和日志复制的关键。

#
★★★

7. Google Spanner 的 TrueTime(原子钟 + GPS 提供有界误差的时间区间)如何通过 commit wait 保证外部一致性(真实时间顺序与提交顺序一致)?工程代价是什么?

Google Spanner 的 TrueTime 如何通过 commit wait 保证外部一致性?工程代价是什么?

  • TrueTime 的时间区间(区间误差)
  • commit wait 机制
  • 外部一致性与工程代价

Google Spanner 用 TrueTime(结合 GPS 和原子钟)提供带误差界的时间区间 [t_earliest, t_latest],即每个事务时间戳被赋予一个不确定区间 [t, t+ε]。为保证外部一致性(真实时间顺序与提交顺序一致,即事务 T1 提交后开启的事务必须读到 T1 的提交),Spanner 在提交时执行 commit wait:在事务提交后,等待时间过去 ε(误差区间界限),确保所有读取都能看到该事务的提交。这样靠"物理时间 + 有界误差 + 等待 ε"实现全局一致的时间戳排序,无需分布式锁。工程代价:提交延迟增加 ε(实际约几毫秒到十几毫秒),需要昂贵的时间基础设施(GPS/原子钟)保证 ε 有界且小,且跨数据中心部署复杂。

Spanner 的独特之处是用"物理时间 + 有界误差"而非逻辑时钟来实现全局一致。commit wait 通过等待误差界消除时间戳不确定,从而保证外部一致性。代价是提交延迟(等 ε)和昂贵的时间基础设施。这解释了为何 Spanner 强大但成本高。对比 HLC用逻辑计数器避免等待。

#
★★★

8. 混合逻辑时钟(HLC)如何用物理时钟 + 逻辑计数器在无需紧密时钟同步下提供因果序?CockroachDB/YugabyteDB 如何基于 HLC 处理读的不确定性区间(uncertainty interval)?

混合逻辑时钟(HLC)如何用物理时钟 + 逻辑计数器在无需紧密时钟同步下提供因果序?CockroachDB/YugabyteDB 如何基于 HLC 处理读的不确定性区间(uncertainty interval)?

  • HLC 的物理时钟 + 逻辑计数器
  • 因果序与时钟同步无关
  • uncertainty interval 的处理

混合逻辑时钟(HLC)把物理时间戳与逻辑计数器结合:正常情况下取物理时钟值,当发现收到的消息时间戳大于本地物理时钟时,用逻辑计数器推进,从而(在无需紧密时钟同步的情况下)提供因果序(causal order)——保证"先发生"的事件获取较小的 HLC 时间戳。HLC 值始终接近物理时间,且满足因果序,可兼得物理时钟的可读性与逻辑时钟的因果性。CockroachDB/YugabyteDB 基于 HLC 实现事务,但物理时钟存在偏差(时钟漂移),导致 HLC 也不完全精确,因此读操作需要处理"不确定性区间"(uncertainty interval):当一个事务的时间戳落在可能因时钟漂移而含糊的区间时,读取器会主动等待或重新读取,以确保读到的是该时间戳对应的已提交状态,从而保证线性一致性/快照隔离。

HLC 解决了"物理时钟缺因果、逻辑时钟缺时间"的问题,用逻辑计数器补足因果性。但物理时钟漂移仍带来不确定性,CockroachDB 用 closed timestamp 和 uncertainty interval 处理:读取时间戳落在不确定区间时,等待该区间的 closed 化或重读。这是"用逻辑序 + 物理时间近似"实现分布式事务的工程做法。

#
★★★

9. BASE 理论(Basically Available、Soft state、Eventual consistency)的应用?

BASE 理论是什么?Basically Available、Soft state、Eventual consistency 如何应用?

  • BASE 的三个要素
  • 软状态与最终一致
  • BASE 的应用场景

BASE 理论是 CAP 中 AP 倾向的工程化原则,包含三个要素:Basically Available(基本可用)——系统在部分故障时仍能提供有限可用性(如降级、限流);Soft state(软状态)——允许系统存在中间状态(数据副本间暂时不一致);Eventual consistency(最终一致)——在不作更新后,系统经过一段时间最终收敛到一致状态。BASE 应用:分布式缓存、消息队列、NoSQL(如 Cassandra、DynamoDB)、微服务异步解耦等,接受短暂不一致以换取高可用与高性能。BASE 与 ACID 相对,ACID 追求强一致,BASE 追求最终一致。

BASE 是"降低一致性要求换取可用性/性能"的设计哲学。它不追求事务的强一致,而是保证"最终一致"、"基本可用"。实际系统常混合使用:核心交易用 ACID/强一致,非核心场景用 BASE。理解 BASE 有助于在架构设计中权衡一致性与可用性。

#
★★★

10. Multi-Raft 分片共识(每个 Region/Tablet 一个 Raft 组)在工程上如何共享传输、存储引擎与心跳以降低成本?元数据管理与再平衡有哪些挑战?

Multi-Raft 分片共识(每个 Region/Tablet 一个 Raft 组)在工程上如何共享传输、存储引擎与心跳以降低成本?元数据管理与再平衡有哪些挑战?

  • Multi-Raft 的架构
  • 共享传输/存储/心跳的优化
  • 元数据管理与再平衡的挑战

Multi-Raft 是分布式数据库(如 TiDB、CockroachDB)的做法:把数据分成多个 Region(Tablet),每个 Region 是一个独立的 Raft 组,各自选主、复制、故障转移。为降低成本,工程上多个 Raft 组共享底层资源:共享传输层(同一节点上的多个 Raft 组复用同一条网络连接和消息线程)、共享存储引擎(所有 Region 的数据落在同一个 RocksDB 等引擎,统一管理)、共享心跳(各 Region 的 leader 心跳合并上报,减少心跳消息数量)。这样避免每个 Region 都独立建连接/独立 storage 的开销。挑战在于:元数据管理——需要维护 Region 到节点的映射(PD/TiKV 的 Placement Driver、CockroachDB 的 meta ranges),管理海量 Region 的路由与状态;再平衡——Region 分裂、合并、迁移(跨节点搬迁数据)时如何保持均衡、不中断服务、控制迁移对性能的影响,以及处理热点 Region。

Multi-Raft 的价值是"以 Raft 组为单元做一致性,同时通过共享资源控制成本"。共享传输、存储、心跳是实现大规模多 Raft 组的关键优化。元数据管理与再平衡则是其运维难点:元数据要精确路由、海量管理;再平衡要均衡、平滑、低影响。这是分布式数据库横向扩展能力的核心。

#
★★★

11. CDC 的实现,基于 binlog(WAL、Debezium)、基于触发器、基于时间戳?

CDC(Change Data Capture)的实现方式有哪些?基于 binlog(WAL、Debezium)、基于触发器、基于时间戳各有什么特点?

  • CDC 的实现方式分类
  • binlog/WAL 解析
  • 触发器与时间戳的适用场景

CDC 的实现方式主要有三种:其一,基于 binlog/WAL(日志)——解析数据库的变更日志(MySQL binlog、PostgreSQL WAL、MongoDB oplog),把变更事件流式输出,如 Debezium、Canal、Flink CDC。优点是无侵入、实时、捕获完整变更(含删除、更新前值)、性能影响小,是主流方案;其二是基于触发器——在表上建触发器,每次变更把变更写入日志表,再轮询/消费。缺点是有侵入、影响写性能、需维护触发器、可能漏绑,适合小规模。其三是基于时间戳/轮询——定时查询带时间戳的变更字段(如 last_updated),捕获新增或修改。缺点是只能捕获可识别时间戳的变更、无法捕获删除、实时性差、有延迟。选型上,日志型 CDC 最通用可靠。

三种 CDC 的核心差异是"变更来源与实时性、侵入性"。日志型无侵入、实时、完整,是生产首选(Debezium/Flink CDC);触发器型侵入且影响性能;时间戳型简单但有限。理解各方案取舍,能根据业务(实时性、删除捕获、侵入容忍)选择 CDC 方案。

#
★★

12. Flink CDC 与 Debezium 的核心差异(Flink CDC 以 Flink 作业运行、支持无锁全量+增量衔接与 exactly-once;Debezium 依托 Kafka Connect 生态)是什么?如何选型?

Flink CDC 与 Debezium 的核心差异是什么?如何选型?

  • Flink CDC 的特性
  • Debezium 的特性
  • 选型依据

Flink CDC 与 Debezium 都是基于 binlog/WAL 的 CDC 工具,但架构不同。Flink CDC 以 Flink 作业(Flink SQL/DataStream)运行,内嵌连接器,支持无锁全量 + 增量衔接(增量快照算法,避免全局锁),并提供了 exactly-once 语义(配合 Flink 的 checkpoint 和两阶段提交),能直接做流处理/计算。Debezium 依托 Kafka Connect 生态,作为 Source Connector 把变更事件发布到 Kafka,依赖 Kafka 作为消息管道,语义通常为 at-least-once,配合下游去重实现 exactly-once。选型:如果已有 Flink 流处理体系、需要计算与 exactly-once,选 Flink CDC;如果已有 Kafka Connect 生态、需要把变更可靠地送进 Kafka 供多下游消费,选 Debezium。两者也可结合(Debezium 采集到 Kafka,Flink 消费计算)。

两者的核心差异是"运行引擎与生态"。Flink CDC 是流处理引擎内的 CDC,强在计算与 exactly-once;Debezium 是 Kafka Connect 生态的组件,强在接入 Kafka 与成熟配置。选型取决于现有技术栈(Flink vs Kafka Connect)与对 exactly-once 的需求。理解差异能避免选错 CDC 工具。

#
★★

13. CDC 管道如何处理 schema 演进(加列、改类型、删列)?Debezium 事件结构与 Schema Registry 兼容策略(BACKWARD/FORWARD/FULL)如何配合下游不中断?

CDC 管道如何处理 schema 演进(加列、改类型、删列)?Debezium 事件结构与 Schema Registry 兼容策略如何配合下游不中断?

  • schema 演进的类型
  • Debezium 事件结构
  • Schema Registry 兼容策略

CDC 管道面对 schema 演进(加列、改类型、删列)时,需要保证下游消费者不被破坏。Debezium 输出的变更事件包含 schema 部分(描述表结构)与 payload 部分(变更数据),schema 中带 version 字段。当源表 schema 变化时,Debezium 会生成新的 schema 版本,并通过配置的 Schema Registry(如 Confluent Schema Registry)管理演进。Schema Registry 的兼容策略:BACKWARD(向后兼容)——新 schema 能读取旧 schema 的数据,允许删列/加带默认值列,保证新消费者可读旧数据;FORWARD(向前兼容)——旧 schema 能读取新 schema 的数据,允许加列,保证旧消费者可读新数据;FULL(全兼容)——同时满足前向与后向。配合策略:下游消费端按兼容策略升级 schema,加列用 FORWARD/FULL(旧消费者可读新数据),改类型/删列用 BACKWARD 并保证新消费者可读旧数据。这样 schema 演进不中断下游消费。

schema 演进是 CDC 的难点,因为变更数据要落到下游 schema 固定的表。核心是用"事件结构 + Schema Registry 兼容策略"管理版本演进。加列通常兼容(FORWARD),删列/改类型需 BACKWARD 或下游同步调整。理解兼容策略能保证 CDC 管道在 schema 变化时平滑演进、不中断。

#
★★

14. Debezium 增量快照算法(按主键切分 chunk、chunk 间用低水位/高水位与 binlog 对齐,1.6+ 通过 signal 表触发)如何实现无全局锁的全量增量衔接?与旧版全局锁快照有何差异?

Debezium 增量快照算法如何实现无全局锁的全量增量衔接?与旧版全局锁快照有何差异?

  • 增量快照的 chunk 切分
  • 低水位/高水位与 binlog 对齐
  • signal 表触发

Debezium 增量快照(Incremental Snapshot,1.6+)用于无全局锁地完成全量 + 增量衔接。它把表按主键切分成多个 chunk,逐个 chunk 读取全量数据;读取每个 chunk 时记录 binlog 的低水位/高水位(LSN/offset),并持续捕获该 chunk 读取期间的 binlog 变更,通过"chunk 数据 + 期间 binlog"对齐,保证该 chunk 的数据不遗漏。chunk 之间继续捕获 binlog,真正发生变更的行已包含在 binlog 中,因此无需全局锁。1.6+ 通过 signal 表(如 _signal 表插入信号)触发增量快照,可用 INSERT INTO ... SNAPSHOT 命令控制。相比旧版全局锁快照:旧版在快照期间对表加全局锁(Locking Snapshot)阻止写,保证一致但阻塞业务;增量快照无全局锁、不阻塞写、可并发,极大地降低了对在线业务的影响。

旧版全局锁快照在快照期间锁表,保证一致性但影响业务;增量快照通过"chunk 分片 + binlog 对齐"实现在不锁表的情况下保证数据不丢、不重、不漏。这是 Debezium/Flink CDC 无锁读的新技术。其关键是对齐机制(chunk 数据与 binlog 变更去重),以及 signal 表触发的新接口。理解它能合理选择全量迁移方式。

#
★★

15. CDC 的消费链路,Debezium → Kafka → 下游消费?

CDC 的消费链路是什么?Debezium → Kafka → 下游消费如何工作?

  • CDC 消费链路架构
  • Debezium 到 Kafka 的接入
  • 下游消费与一致消费

CDC 的典型消费链路是:源数据库 → Debezium(Source Connector)→ Kafka(消息管道)→ 下游消费(如 Flink、数据仓库、缓存、搜索引擎)。Debezium 作为 Kafka Connect 的 Source Connector,持续解析源库 binlog/WAL,把变更事件发布到 Kafka 的 topic;下游应用从 Kafka 消费 topic,按变更事件更新目标系统(如同步到数仓、刷新缓存、构建索引)。Kafka 提供消息持久化、顺序与多消费者,保证变更事件的可靠传递与解耦。下游消费可实现 at-least-once(配合幂等去重)或 exactly-once(配合事务/幂等写入)。这一链路是"数据库变更 → 异步同步到其他系统"的标准模式。

该链路的核心价值是"把数据库变更异步可靠地同步到下游系统",Kafka 作为中间缓冲解耦了源库与下游。Debezium 负责采集,Kafka 负责传输与持久化,下游按需消费。理解链路各环节(采集、传输、消费、一致性)是设计 CDC 数据同步的基础。

#
★★

16. CDC(Change Data Capture)的概念,捕获数据库变更事件?

CDC(Change Data Capture)的概念是什么?如何捕获数据库变更事件?

  • CDC 的定义
  • 变更事件的来源
  • CDC 的用途

CDC(Change Data Capture,变更数据捕获)是一种技术,用于捕获数据库中的数据变更(插入、更新、删除)事件,并将其流式输出给下游系统,实现数据同步、实时分析、事件驱动等。变更事件通常来自数据库的变更日志(MySQL binlog、PostgreSQL WAL、MongoDB oplog),通过解析日志还原出每次变更的完整信息(变更前值、变更后值、主键、时间戳)。CDC 的用途包括:数据同步(DB → 数仓/缓存/搜索引擎)、实时分析、微服务间解耦、审计、缓存刷新。相比应用层双写,CDC 无侵入、实时、可靠,能捕获所有(包括旁路)变更。

CDC 的核心是"从日志捕获变更,而非应用主动上报"。它把"数据库变更"变成"可消费的事件流",是数据同步与实时数据架构的基础。理解 CDC 概念与来源,是理解 Debezium、Canal、Flink CDC 等工具的前提。

#
★★

17. Debezium 的工作原理与应用场景?

Debezium 的工作原理是什么?有哪些应用场景?

  • Debezium 的架构
  • 工作原理
  • 应用场景

Debezium 是一个开源的 CDC 工具,基于 Kafka Connect 生态,作为 Source Connector 运行。它通过内置的数据库连接器(如 MySQL、PostgreSQL、MongoDB 连接器)解析源库的 binlog/WAL/oplog,把变更事件转换为统一格式(含 schema 与 payload 的 JSON/Avro),发布到 Kafka 的 topic。它支持快照(全量)与增量(流式)两种捕获,并支持断点续传(通过 offset 记录已消费位置)。应用场景:数据同步(数据库到数仓/缓存/搜索引擎)、实时数据处理(与 Flink/Kafka Streams 结合)、事件驱动架构、审计与合规、微服务数据解耦。Debezium 的优势是无侵入、实时、支持多种数据库、可扩展。

Debezium 的核心是"把数据库变更变成 Kafka 事件流"。它作为 Kafka Connect 连接器,负责采集与统一格式,Kafka 负责传输。其断点续传(offset)保证不丢事件。应用场景围绕"数据库变更的实时同步与消费"。理解 Debezium 工作原理是使用 CDC 数据管道的基础。

#
★★

18. CDC 的一致性保证,at-least-once、exactly-once?

CDC 的一致性保证是什么?at-least-once 与 exactly-once 如何实现?

  • at-least-once 语义
  • exactly-once 语义
  • 与下游幂等配合

CDC 的一致性保证通常涉及 at-least-once 与 exactly-once。at-least-once(至少一次)——每个变更事件至少被处理一次,可能重复,需下游幂等去重;这是大部分 Kafka 消费(含 Debezium)的默认语义,因为 offset 提交与处理可能因失败而重试导致重复。exactly-once(恰好一次)——每个变更事件恰好被处理一次,需要"处理与副作用原子化"(如 Kafka 事务 + 幂等写入,或 Flink 的 checkpoint + 两阶段提交)。实现 exactly-once 通常配合:源端记录 offset、下游幂等写入(以主键去重)、中转(Kafka)事务性提交。实际中,多数 CDC 链路用 at-least-once + 下游幂等实现"最终恰好一次"的效果。

CDC 一致性取决于"采集端 offset 管理与下游消费端幂等"。at-least-once 是基础,靠下游幂等去重;exactly-once 需要端到端事务或幂等写入。理解这些语义能合理设计 CDC 数据管道,避免重复或丢失数据。Flink CDC 通过 checkpoint 提供 exactly-once,Debezium + Kafka 需配合幂等消费。

#

19. XA 协议(两阶段提交)的实现与局限?

XA 协议(两阶段提交)是如何实现的?有什么局限?

  • XA 的两阶段提交流程
  • 资源与事务管理器
  • XA 的局限

XA(两阶段提交)是实现分布式事务的协议,涉及事务管理器(TM)与资源管理器(RM,如数据库)。两阶段:准备阶段(Prepare)——TM 让所有 RM 完成准备并持久化,返回就绪;提交阶段(Commit/Abort)——若所有 RM 都就绪,TM 通知所有 RM 提交,否则回滚。这样保证所有 RM 要么全部提交、要么全部回滚,实现强一致的原子性。局限:其一,阻塞问题——两阶段提交期间资源被锁定,若协调者(TM)故障,参与者可能长期阻塞,无法释放;其二,性能差——多轮网络交互、锁持有时长长,吞吐低;其三,协调者单点——TM 故障可能导致事务悬挂;其四,不支持长事务与复杂补偿。因此 XA 适合短暂、强一致、低并发场景(如早期银行交易),而对高并发、长流程、微服务场景,多用 Saga/TCC/最终一致方案。

XA 的本质是"集中协调 + 两阶段决议"实现强一致原子性,但代价是阻塞、锁、协调者单点。经典银行系统用 XA 保证资金原子,但分布式高并发场景下其性能瓶颈和阻塞风险突出。理解 XA 的流程与局限,是理解分布式事务演进(TCC、Saga)的基础。