可靠性与幂等
1. 这是什么
可靠性与幂等关注的是消息是否会丢、是否会重、业务是否能安全重复处理。
这是 Kafka 在生产系统里最关键的能力之一。
一句话理解:
- 可靠性关注“消息链路稳不稳”
- 幂等关注“重复来一次会不会出事故”
2. 为什么重要
消息系统最怕的不是“偶尔慢一点”,而是:
- 消息丢了
- 重复消费
- 业务重复执行
所以 Kafka 的可靠性配置和业务幂等设计必须一起看。
3. 先建立直觉:开启幂等生产者不等于业务绝对不会重复
一个很常见的误区是:
- 只要 Kafka 开了幂等,业务就永远不会重复
这不准确。
更实用的理解是:
- 中间件可以降低链路层重复
- 但业务最终是否能安全重复处理,仍然常常要靠消费端幂等
4. 核心内容
4.1 acks
acks 决定的是:
- Producer 发送后,要等到什么程度才算成功
所以它直接影响:
- 可靠性
- 延迟
- 吞吐
4.2 重试
重试是可靠性的重要组成部分,但重试本身也会带来:
- 乱序风险
- 重复风险
- 额外压力
4.3 幂等生产者
幂等生产者的核心目标是:
- 降低同一条消息因为重试等原因重复写入的概率
它很重要,但不等于:
- 整条业务链天然幂等
4.4 事务消息基础认知
学习阶段先抓住一个直觉:
- Kafka 事务更多是在消息链路层做一组操作的一致性控制
它不是替代业务数据库事务的万能工具。
4.5 至少一次、至多一次、恰好一次
这是消息语义最核心的三种表达:
- 至少一次:可能重复,不轻易丢
- 至多一次:可能丢,不重复
- 恰好一次:目标最好,但实现最复杂
4.6 消费端幂等
消费端幂等常见做法包括:
- 业务唯一键
- 去重表
- 状态机控制
- 幂等 key
5. 学习重点
这一章最重要的是掌握:
- 可靠性和吞吐通常存在权衡
acks只是链路参数,不是全部答案- 幂等生产者很重要,但消费端幂等常常更关键
- “恰好一次”比想象中复杂得多
6. 常见问题
6.1 只调 acks 不看整体链路
这样容易把中间件参数当成万能保险。
6.2 误以为开启幂等后业务就绝对不会重复
业务层去重和状态控制仍然非常重要。
6.3 忽视消费端去重与状态控制
这是很多重复执行事故的真正根因。
7. 动手验证
当前环境没有 Kafka CLI,这里用纯 Java demo 直接验证“重试可能带来重复、幂等能消除重复影响”的核心心智。
7.1 准备一个可运行示例
新建文件 KafkaIdempotenceDemo.java,内容如下:
java
import java.util.HashSet;
import java.util.Set;
public class KafkaIdempotenceDemo {
public static void main(String[] args) {
String eventId = "evt-1001";
// 不做幂等:重试两次就执行两次
int nonIdempotentCounter = 0;
nonIdempotentCounter++;
nonIdempotentCounter++;
System.out.println("nonIdempotentCounter=" + nonIdempotentCounter);
// 做幂等:同一个事件只处理一次
Set<String> processed = new HashSet<>();
int idempotentCounter = 0;
if (processed.add(eventId)) {
idempotentCounter++;
}
if (processed.add(eventId)) {
idempotentCounter++;
}
System.out.println("idempotentCounter=" + idempotentCounter);
System.out.println("processedSize=" + processed.size());
}
}7.2 编译并运行
bash
javac KafkaIdempotenceDemo.java
java KafkaIdempotenceDemo7.3 你应该观察到什么
text
nonIdempotentCounter=2
idempotentCounter=1
processedSize=17.4 每一行在验证什么
nonIdempotentCounter=2:说明重试或重复消息会直接导致业务重复执行idempotentCounter=1:说明幂等控制能把重复消息对业务的影响压平processedSize=1:说明同一事件 ID 只被记一次
8. 练习建议
- 总结 Kafka 常见消息语义的适用场景
- 设计一个消费端幂等方案
- 对比生产端配置对可靠性的影响
- 用自己的话解释“为什么恰好一次比至少一次复杂得多”
9. 自测问题
acks配置会如何影响可靠性和性能?- 为什么消息系统里幂等几乎是必备能力?
- “恰好一次”为什么比想象中复杂?
- 为什么消费端幂等常常比中间件配置更关键?
10. 自测核对要点
- 可靠性和性能通常存在权衡
acks、重试、幂等生产者共同影响链路语义- 消费端幂等是关键防线
- “恰好一次”不是简单一个开关,而是整条链路协同结果