【问题标题】:Spring Integration to read message from Kafka topic based on timestamp基于时间戳从 Kafka 主题读取消息的 Spring 集成
【发布时间】:2019-07-06 23:11:29
【问题描述】:

在使用 spring kafka 时,我可以使用以下代码根据时间戳读取主题中的消息 -

                ConsumerRecords<String, String> records = consumer.poll(100);
                if (flag) {
                    Map<TopicPartition, Long> query = new HashMap<>();
                    query.put(new TopicPartition(kafkaTopic, 0), millisecondsFromEpochToReplay);

                    Map<TopicPartition, OffsetAndTimestamp> result = consumer.offsetsForTimes(query);
                    if(result != null)
                    {
                        records = ConsumerRecords.empty();
                    }

                    result.entrySet().stream()
                            .forEach(entry -> consumer.seek(entry.getKey(), entry.getValue().offset()));

                    flag = false;
                }

如何使用 spring integration DSL 实现相同的功能 - 使用 KafkaMessageDrivenChannelAdapter? 我们如何设置集成流程并根据时间戳从主题中读取消息?

【问题讨论】:

    标签: spring-integration kafka-consumer-api spring-integration-dsl


    【解决方案1】:

    使用ConsumerAwareRebalanceListener 配置适配器的侦听器容器,并在分配分区时执行查找/查找。

    编辑

    使用 Spring Boot(但您可以通过创建容器来配置容器)...

    spring.kafka.consumer.enable-auto-commit=false
    spring.kafka.consumer.auto-offset-reset=earliest
    spring.kafka.consumer.group-id=so54664761
    

    @SpringBootApplication
    public class So54664761Application {
    
        public static void main(String[] args) {
            SpringApplication.run(So54664761Application.class, args);
        }
    
        @Bean
        public ApplicationRunner runner(KafkaTemplate<String, String> template) {
            return args -> template.send("so54664761", "foo");
        }
    
        @Bean
        public NewTopic topic() {
            return new NewTopic("so54664761", 1, (short) 1);
        }
    
        @Bean
        public IntegrationFlow flow(ConcurrentKafkaListenerContainerFactory<String, String> containerFactory) {
            ConcurrentMessageListenerContainer<String, String> container = container(containerFactory);
            return IntegrationFlows.from(new KafkaMessageDrivenChannelAdapter<>(container))
                    .handle(System.out::println)
                    .get();
        }
    
        @Bean
        public ConcurrentMessageListenerContainer<String, String> container(
                ConcurrentKafkaListenerContainerFactory<String, String> containerFactory) {
    
            ConcurrentMessageListenerContainer<String, String> container = containerFactory.createContainer("so54664761");
            container.getContainerProperties().setConsumerRebalanceListener(new ConsumerAwareRebalanceListener() {
    
                @Override
                public void onPartitionsAssigned(Consumer<?, ?> consumer, Collection<TopicPartition> partitions) {
                    System.out.println("Partitions assigned - do the lookup/seeks here");
                }
    
            });
            return container;
        }
    
    }
    

    Partitions assigned - do the lookup/seeks here
    GenericMessage [payload=foo, headers={kafka_offset=0, kafka_consumer=org.apache.kafka.clients.consumer.KafkaConsumer@2f5b2297, kafka_timestampType=CREATE_TIME, kafka_receivedMessageKey=null, kafka_receivedPartitionId=0, kafka_receivedTopic=so54664761, kafka_receivedTimestamp=1550241100112}]
    

    【讨论】:

    • 例如here.
    • 谢谢@Gary,我是新手,所以需要帮助了解我们如何在 Spring Integration DSL 中注入 ConsumerAwareRebalance Listener,我的流程看起来像
    • 查看我的答案的编辑;它使用 Boot 的自动配置容器工厂,但是您可以将侦听器添加到容器属性中,但您可以创建容器。
    • 感谢加里的帮助。如果我们想在同一个消费者组中有多个消费者,我们应该设置 ConcurrentMessageListenerContainer 的并发级别吗?上面的配置怎么设置多个消费者呢?
    • 使用Spring Boot时,spring.kafka.consumer.concurrency=5;自己创建容器时container.setConcurrency(5).
    猜你喜欢
    • 1970-01-01
    • 2022-01-06
    • 1970-01-01
    • 2019-08-10
    • 2021-03-01
    • 1970-01-01
    • 1970-01-01
    • 2019-10-06
    • 1970-01-01
    相关资源
    最近更新 更多