Kafka中unclean.leader.election.enable参数的内涵
官网说明:http://kafka.apache.org/documentation/#configuration
参考上图,某种状态下,follower2副本落后leader副本很多,并且也不在leader副本和follower1副本所在的ISR(In-Sync Replicas)集合之中。follower2副本正在努力的追赶leader副本以求迅速同步,并且能够加入到ISR中。但是很不幸的是,此时ISR中的所有副本都突然下线,情形如下图所示:
此时follower2副本还在,就会进行新的选举,不过在选举之前首先要判断unclean.leader.election.enable参数的值。如果unclean.leader.election.enable参数的值为false,那么就意味着非ISR中的副本不能够参与选举,此时无法进行新的选举,此时整个分区处于不可用状态。如果unclean.leader.election.enable参数的值为true,那么可以从非ISR集合中选举follower副本成为新的leader。
我们进一步考虑unclean.leader.election.enable参数为true的情况,在上面的这种情形中follower2副本就顺其自然的称为了新的leader。随着时间的推进,新的leader副本从客户端收到了新的消息,如上图所示。
此时,原来的leader副本恢复,成为了新的follower副本,准备向新的leader副本同步消息,但是它发现自身的LEO比leader副本的LEO还要大。Kafka中有一个准则,follower副本的LEO是不能够大于leader副本的,所以新的follower副本就需要截断日志至leader副本的LEO处。
如上图所示,新的follower副本需要删除消息4和消息5,之后才能与新的leader副本进行同步。之后新的follower副本和新的leader副本组成了新的ISR集合,参考下图。
原本客户端已经成功的写入了消息4和消息5,而在发生日志截断之后就意味着这2条消息就丢失了,并且新的follower副本和新的leader副本之间的消息也不一致。也就是说如果unclean.leader.election.enable参数设置为true,就有可能发生数据丢失和数据不一致的情况,Kafka的可靠性就会降低;而如果unclean.leader.election.enable参数设置为false,Kafka的可用性就会降低。具体怎么选择需要读者更具实际的业务逻辑进行权衡,可靠性优先还是可用性优先。从Kafka 0.11.0.0版本开始将此参数从true设置为false,可以看出Kafka的设计者偏向于可靠性,如果能够容忍uncleanLeaderElection场景带来的消息丢失和不一致,可以将此参数设置为之前的老值——true。