如何在KafkaListener中不提交偏移量

时间:2020-03-06 07:18:12

标签: apache-kafka spring-kafka

我正在使用KafkaListener,并且希望基于是否成功处理消息来控制偏移量的提交。为此,我正在使用下面的代码,但它会在nack(index,sleep)上引发异常:

    @KafkaListener(topics="topic-name", groupId="group"){
    someMethod(@Header(KafkaHeaders.OFFSET) int offset, Acknowlegement ack, String message){
       try{
           processMessage(message);
           ack.acknowledge();
       }catch(Exception e){
           ack.nack(offset, 1000);
       }
    }

我已将ackMode设置为Manual,并且Auto Commit属性设置为false。消息处理失败时,nack会引发异常:

      Exception: nack(index, sleep) is not supported by this Acknowledgement.

也欢迎使用其他任何方式处理该情况。

1 个答案:

答案 0 :(得分:0)

nack(index, sleep)用于批处理侦听器List<String> messages。索引是告诉容器列表中的哪个消息失败。

对于记录侦听器,请使用nack(sleep)-容器已经知道哪个记录失败了。

请参见the documentation

从2.3版开始,Acknowledgment接口具有两个附加方法nack(long sleep)nack(int index, long sleep)。第一个与记录侦听器一起使用,第二个与批处理侦听器一起使用。为您的侦听器类型调用错误的方法将引发IllegalStateException

使用记录侦听器,当调用nack()时,将提交任何待处理的偏移量,最后一次轮询的剩余记录将被丢弃,并对它们的分区执行查找,以便将失败的记录和未处理的记录重新传递到磁盘上。下一个poll()。通过设置sleep参数,可以在重新交付之前暂停使用者线程。这与在容器中配置了SeekToCurrentErrorHandler时引发异常的功能类似。

使用批处理侦听器时,可以在发生故障的批处理中指定索引。调用nack()时,将在对失败和废弃记录的分区执行索引和查找之前为记录提交偏移量,以便在下一个poll()中重新传递它们。这是对SeekToCurrentBatchErrorHandler的改进,后者只能搜索整个批次进行重新交付。