面试题答案
一键面试生产者端保障消息可靠性投递机制
- ACK机制
- 配置:生产者通过
acks
参数配置ACK机制。acks
有三个可选值:acks = 0
:生产者在发送消息后,不需要等待任何来自broker的确认,就会继续发送下一条消息。这种情况下,生产者的吞吐量最高,但消息可靠性最低,因为如果broker没有收到消息,生产者不会知道。acks = 1
:生产者在发送消息后,只要leader副本成功写入消息,就会收到broker的确认。这种情况下,如果leader副本在确认后但在follower副本同步前发生故障,消息可能会丢失。acks = all
(或acks = -1
):生产者在发送消息后,需要等待所有同步副本(ISR中的副本)都成功写入消息,才会收到broker的确认。这提供了最高的消息可靠性,但吞吐量相对较低。
- 作用:ACK机制确保生产者知晓消息是否成功被broker接收和存储,通过合理配置
acks
可以在消息可靠性和吞吐量之间进行权衡。
- 配置:生产者通过
- 重试机制
- 配置:生产者通过
retries
参数配置重试次数,默认值为0。通过retry.backoff.ms
参数配置重试间隔时间,默认值为100。 - 作用:当生产者发送消息失败时(如网络瞬时故障等原因),可以根据配置的重试次数和间隔时间进行重试,增加消息成功发送的可能性,保障消息的可靠性。
- 配置:生产者通过
- 幂等性
- 配置:生产者通过设置
enable.idempotence
为true
开启幂等性,开启幂等性后,acks
会被自动设为all
,retries
会被自动设为Integer.MAX_VALUE
。 - 作用:幂等性确保生产者即使在发生重试的情况下,也不会重复写入相同的消息到broker,避免消息重复带来的问题,进一步保障消息的可靠性。
- 配置:生产者通过设置
消费者端保障消息可靠性投递机制
- 位移提交策略
- 自动提交:
- 配置:通过
enable.auto.commit
参数设置为true
开启自动提交,通过auto.commit.interval.ms
参数设置自动提交的时间间隔,默认值为5000毫秒。 - 对消息可靠性影响:自动提交位移简单方便,但可能会导致消息重复消费。因为在自动提交位移后,如果消费者在处理消息过程中发生故障,下次重新消费时,会从已提交的位移处开始,可能导致部分已处理但未提交位移的消息再次被处理。
- 配置:通过
- 手动提交:
- 配置:通过
enable.auto.commit
参数设置为false
关闭自动提交,手动调用commitSync()
或commitAsync()
方法提交位移。 - 对消息可靠性影响:手动提交位移可以确保消费者在完全处理完消息后再提交位移,从而避免消息重复消费。
commitSync()
是同步提交,会阻塞当前线程直到提交成功,可靠性高但可能影响性能;commitAsync()
是异步提交,不会阻塞线程,但可能会因为提交过程中的故障而导致提交失败,不过可以通过回调函数进行处理。所以手动提交可以更好地保障消息的可靠性,但需要开发者更加谨慎地管理位移提交的时机。
- 配置:通过
- 自动提交:
- 消费组分区分配策略
- Range策略:将主题的分区按照消费者数量进行平均分配。例如,有3个分区(P0、P1、P2)和2个消费者(C0、C1),则C0可能分配到P0、P1,C1分配到P2。如果分区数量不能被消费者数量整除,可能导致部分消费者分配到更多分区,影响负载均衡,进而可能影响消息消费的可靠性。
- RoundRobin策略:将主题的所有分区依次轮流分配给各个消费者。如上述例子,可能C0分配到P0、P2,C1分配到P1,相对更均衡,但如果消费者处理能力不同,也可能出现负载不均衡影响消息可靠性的情况。
- Sticky策略:尽可能保持上一次的分配方案,如果有新消费者加入或离开,会在尽量少改变分配的基础上进行调整,有助于保持消费的稳定性,保障消息可靠性。