1、问题背景:什么是增量同步?为什么会出现乱序和重复?
大家好,我是这次课程的主讲。先聊聊我自己的经历——几年前我在做一个金融交易系统的数据同步模块,每天要处理上亿条订单变更。那时候我踩过一个坑:明明源端只改了三条记录,同步到目标端却变成了五条,而且顺序全乱了。排查了一整天才发现,问题出在增量同步的乱序和重复上。
嗯,咱们今天就从最基础的问题开始聊。搞清楚什么是增量同步,以及乱序和重复到底是怎么来的。
1.1 什么是增量同步?
说白了,增量同步就是只同步变化的数据,而不是把整个数据集重新搬一遍。
举个例子:你有一个用户表,里面有 1000 万条记录。如果每次同步都全量拷贝,那得传输 1000 万行数据,耗时又耗带宽。但实际业务中,每天可能只有几千条记录新增或修改。增量同步只把这几千条变化数据传过去,效率高得多。
核心思想:只传输变化,不传输全量。
增量同步通常依赖以下几种机制来捕获变化:
| 机制 | 原理 | 常见场景 |
|---|---|---|
| 时间戳/版本号 | 记录每条数据的最后修改时间,同步时只取大于上次同步时间的数据 | 关系型数据库的更新时间字段 |
| 日志解析(CDC) | 解析数据库的 binlog、WAL 等事务日志,提取变更事件 | MySQL binlog、PostgreSQL WAL、Kafka Connect |
| 消息队列 | 应用层将变更事件发布到消息队列,消费者拉取处理 | Kafka、RabbitMQ、Pulsar |
| 触发器/钩子 | 在数据库层面设置触发器,变更时自动记录到变更表 | Oracle 触发器、SQL Server Change Tracking |
我个人习惯用 CDC 方式,因为它对业务代码无侵入,而且能捕获所有数据变更,包括删除操作。不过每种方式都有各自的坑,后面章节我会详细讲。
1.2 为什么会出现乱序?
乱序,就是数据到达目标端的顺序,跟它们在源端发生的顺序不一致。
为什么会这样?你想想看,增量同步通常是一个分布式系统。数据从源端产生,经过网络传输、中间件缓存、多线程处理,最后才落到目标端。这个链条上的每个环节都可能打乱顺序。
我总结了几种常见的乱序场景:
- 网络延迟不均:两条数据几乎同时发出,但走的网络路径不同,后发的反而先到。
- 多分区/多线程处理:数据被分发到不同的分区或线程并行处理,处理速度不同,导致输出顺序错乱。
- 重试机制:某条数据第一次发送失败,重试成功时,它后面的数据已经先被处理了。
- 中间件缓冲:消息队列、缓存层等中间件可能对数据做批量处理或重新排序。
注意:乱序不是 bug,而是分布式系统的固有特性。你无法完全消除乱序,只能通过设计来容忍或纠正它。
我曾经在一个日志采集系统中遇到过这样的问题:A 事件在源端先发生,B 事件后发生。但因为 A 事件的数据量较大,序列化耗时更长,结果 B 事件先到达目标端。下游的聚合计算基于 B 事件做了状态更新,等 A 事件到达时,状态已经不对了。嗯,这就是典型的乱序导致的数据不一致。
1.3 为什么会出现重复?
重复,就是同一条数据被同步了多次。
重复的原因比乱序更隐蔽。我刚开始做分布式系统时,总觉得重复是网络问题导致的,后来才发现,重复的根源在于“至少一次”的投递语义。
来看一个典型的场景:
1. 源端发送数据 D1
2. 目标端收到 D1,处理成功,返回 ACK
3. ACK 在网络中丢失
4. 源端未收到 ACK,认为 D1 发送失败
5. 源端重试,再次发送 D1
6. 目标端再次收到 D1,此时就产生了重复
重复的常见原因包括:
- ACK 丢失:上面这个例子就是典型。
- 超时重试:源端设置了超时时间,目标端处理慢但最终成功了,源端却已经重试了。
- 消费者重启:消息队列的消费者在处理完数据但未提交 offset 时宕机,重启后会重新消费旧消息。
- 幂等性缺失:目标端没有做幂等处理,同样的数据执行多次就会产生多条记录。
我的建议:在设计增量同步系统时,默认假设重复一定会发生。与其花大力气去避免重复,不如在目标端做好去重机制。后面章节我会详细讲几种去重方案。
1.4 乱序和重复带来的影响
乱序和重复不是理论问题,它们会实实在在地影响业务。我列几个典型的后果:
| 问题 | 影响 | 实际案例 |
|---|---|---|
| 数据不一致 | 目标端的数据状态与源端不符 | 订单状态从“已支付”变成“待支付” |
| 计算错误 | 聚合结果、统计指标出错 | 用户余额被重复扣减 |
| 资源浪费 | 重复处理消耗 CPU、内存、带宽 | 同一条日志被处理了 3 次 |
| 下游连锁反应 | 触发告警、影响其他系统 | 重复数据导致风控系统误判 |
我记得有一次,一个电商客户反馈说订单同步后,用户收到了两条相同的发货通知。排查后发现是消息队列的消费者重启导致重复消费,而下游的去重逻辑没覆盖到通知发送这个环节。你看,一个小问题可能引发连锁反应。
1.5 本章知识体系总览
为了让你对本章内容有个整体认识,我画了一张图,把增量同步的核心概念、乱序和重复的成因、以及它们的影响串起来。
这张图把本章的核心内容都串起来了。左边是增量同步的四种常见机制,右边是乱序的四个主要原因,底部是乱序和重复可能带来的影响。你可以把它当作一个知识地图,后面每讲一个具体方案时,都可以回到这张图上看看它解决的是哪个环节的问题。