在实时数仓分层中,Kafka是一种比较常见的中间存储层,而在分布式计算中由于硬件、软件等异常导致的任务重启是一种正常的现象,通过之前的Kafka-Consumer分析得知,offset 是跟随着checkpoint周期性的保存, 那么消息是有可能被重复消费的,而Kafka 作为输出端并不属于整个Flink任务状态的一部分,重复被消费的消息会重复的输出,因此为了保证输出到Kafka数据的一致性,Flink 在Kafka Sink端的事务语义。本篇主要介绍Kafka-Sink 的执行流程与核心设计。
Kafka 幂等与事务
幂等
在通常情况下,生产者发送数据可能由于网络等原因导致数据重复发送, 常见的解法就是幂等操作, 也就是执行多次相同的操作与其执行一次的影响结果是一样的。Kafka 不像MySQL/HBase 这样存储可以通过uniqueKey或者RowKey 机制来保证幂等, 为了实现幂等引入了两个概念producerId与sequenceNumber, 每一个producer 都会有一个由服务端生成的producerId与之对应,sequenceNumber 是partition级别的自增消息序列号,客户端每一条消息都会对应生成一个sequenceNumber,在服务端同样会保存该sequenceNumber, 只有当客户端消息的sequenceNumber 大于服务端存储的sequenceNumber 该消息才会被接受,通过这种方式保证