Kafka 总结

本文深入探讨Kafka的核心概念,包括broker、partition、consumer group等,并详细阐述其存储原理,消息写入、路由及消费流程,以及HW阶段机制,帮助理解Kafka如何保证数据一致性与高可用性。
摘要由CSDN通过智能技术生成

kafka最初的使命是用于存储数据,所以天生会丢消息,一般在重要的业务系统中,都不会使用kafka。

核心概念

  • broker:kafka集群中的一个节点;
  • broker leader:负责而选举partition leader;
  • coordinator:负责维护当前broker中各个partition被消费的offset;
  • topic:kafka中消息的逻辑分类,也可以理解为一个消息通道;
  • partition:为了提高吞吐量,topic被分成了多个partition(分区),partition内的数据有序;
  • segment:每个partition在存储的时候,为了提高读写效率,被分成了多个segment段;
  • consumer:消息的消费者;
  • producer:消息的生产者;
  • consumer group:消费者的一种高可用机制,在消费者组内,一条消息会被互斥消费;
  • deplicas of partition:为了消息的高可用,每个partition会存在多分副本;
  • partition leader:partition的多副本中,会存在一个leader负责数据的读写,其他副本只负责数据备份;
  • partition follower:用于做数据备份的partition;
  • ISR:partition的follower列表;
  • offset:partition中的消息是有序的,每条消息都有一个唯一的偏移量,即offset;
  • rebalance:默认情况下,一个消费者会消费一个或多个partition,或不消费任何partition,但是,当partition的数量发生变化或者consumer的数量发生变化时,对于consumer,partition的所有权就会在consumer之间转移,这个过程就做rebalance;

存储原理

kafka中消息的最小逻辑单元topic,在数据存储的时候,一个topic会被拆分成多个partition,每个partition会分散到集群中的不同节点上,同时,每个partition还会存在多分副本,保证数据的可靠性。

在存储数据时,一个partition对应了磁盘上的一个文件夹,而这个paritition中的消息会被拆分成多个segment,每个segment包含了三个核心文件:

  • segmentname.index 消息偏移量索引文件
  • segmentname.timeindex 以时间为维度的索引文件
  • segment.log 消息文件

索引文件中,是以分段的方式来建立segment中数据的索引,这样就可以尽量减少一次数据检索的范围。

在创建topic的时候,要确定partition的数量是broker数量的整数倍,这样可以避免数据整个集群中发生倾斜。

HW阶段机制

在消费数据时,consumer从partition消费数据,但是并不是partition leader收到消息后,consumer就能够立即消费,而是当所有partition follower都同步完成后,这条消息才对consumer 可见,但是,如果在partition follower同步数据的过程中,partition leader宕机了,此时就会触发broker controller的leader选举,这时候就会从那些与原partition leader数据不一致的partition follower(ISR列表)中选出一个新的leader,但是,过了一段时间后,原partition leader又活过来了,此时,它作为partition follower,为了保证数据的一致性,这个重新活过来的partition follower就会从根据HW阶段机制将自己原有的与现在partition leader不一致的数据截掉。

HW阶段机制包含两个概念:
HW:High Water,高水位,用来标记最后一条被所有follower同步的一条标线;
LEO:Log End Offset:partition leader的接收到的最后一条数据;

当producer向partition 写入数据时,可以通过参数来配置是否需要等到partition leader向follower同步数据,这也是中保证写入数据成功的机制,每写一条消息LEO的offset就会进行调整,但只有当所有follower都将数据同步后,才会调整HW。

消息写入流程

  1. producer从zookeeper中获取partition leader;
  2. 将消息发给partition leader;
  3. partition leader将数据写入本地segment,并通知isr列表中的follower;
  4. partition follower从leader pull 数据并写入本地segment,写入成功后向leader返回ack消息;
  5. leader收到所有follower的ack消息后,返回给producer ack消息,一次写入成功;

发送消息时,可以通过request.required.acks参数来调整发送消息的可靠性:
0:异步发送,表示不需要kafka返回ack消息;
1:只要partition leader收到消息后就立即返回ack;
-1:等待所有partition follower都同步完成后,partition leader再返回producer给ack消息;

发送消息的可靠性主键增高,但是性能会逐渐下降,使用时,需要根据不能的业务场景进行调节。

消息路由规则

通过代码向kafka发送消息的时候,消息被封装成Record,每个Record包含了一个Key和一个消息体,Key主要用来做消息路由,但是也可以不指定Key值,具体的路由规则如下:

  • 若指定了partition,则直接将消息发送到指定的partition;
  • 如果没有执行paritition但指定了key值,那么通过key的哈希值与topic分区数取模来确定发往哪个partition;
  • 若partition和key都没有指定,则通过轮询的方式发送到其中一个partition;

消息消费流程

  1. 消费者订阅指定的topic
  2. Broker Controller给这个消费者分配partition,并将对应的offset发给consumer;
  3. consumer 开始消费消息;
  4. consumer消费完消息后,向对应的Coordinator反馈;
  5. Coordinator更新对应的offset;

重复消费

  • 同一个consumer重复消费
由于Consumer消费能力比较低,导致消费超时,最终offset不会被提交,最终导致重复消费。
  • 不同的consumer重复消费
consumer消费了消息,但还未来得及提交offset就宕机了,
这些已经被消费过的消息会被其他consumer重复消费;

解决办法:

  1. 增加ack消息超时时限;
  2. 设置enable.auto.commit=false,手动进行ack消息的提交;
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值