Flink如何使用具有多个分区的Kafka主题消息,而不会产生偏差?

时间:2017-08-07 07:53:32

标签: event-handling apache-kafka apache-flink flink-streaming

假设我们有一个主题的3个kafka分区,并且我希望我的事件按小时加窗,使用事件时间。

当kafka消费者在当前窗口之外时,是否会停止从分区读取?还是打开一个新窗口?如果它打开了新的窗口,那么理论上如果一个分区的事件时间与其他分区相比会非常偏斜,理论上不可能打开无限量的窗口并因此耗尽内存。当我们重播一些历史时,这种情况尤其可能。

我一直试图从阅读文档中得到这个答案,但是在分区上找不到Flink与Kafka的内部结构。关于这个特定主题的一些好的文档将非常受欢迎。

谢谢!

3 个答案:

答案 0 :(得分:0)

您可以尝试使用此类型的

public void runStartFromLatestOffsets() throws Exception {
        // 50 records written to each of 3 partitions before launching a latest-starting consuming job
        final int parallelism = 3;
        final int recordsInEachPartition = 50;

        // each partition will be written an extra 200 records
        final int extraRecordsInEachPartition = 200;

        // all already existing data in the topic, before the consuming topology has started, should be ignored
        final String topicName = writeSequence("testStartFromLatestOffsetsTopic", recordsInEachPartition, parallelism, 1);

        // the committed offsets should be ignored
        KafkaTestEnvironment.KafkaOffsetHandler kafkaOffsetHandler = kafkaServer.createOffsetHandler();
        kafkaOffsetHandler.setCommittedOffset(topicName, 0, 23);
        kafkaOffsetHandler.setCommittedOffset(topicName, 1, 31);
kafkaOffsetHandler.setCommittedOffset(topicName, 2, 43);

答案 1 :(得分:0)

因此,首先来自Kafka的所有事件都会不断阅读,而进一步的窗口操作对此没有影响。在谈论内存不足时,还有很多事情需要考虑。

  • 通常你不会为窗口存储每个事件,而只是为事件存储一些事件
  • 每当窗口关闭时,相应的内存都被释放。

更多关于Kafka消费者如何与EventTime互动(特别是水印,你可以查看here

答案 2 :(得分:0)

这可能会帮助您获得清晰度

https://github.com/apache/flink/blob/release-1.2/flink-connectors/flink-connector-kafka-base/src/main/java/org/apache/flink/streaming/connectors/kafka/partitioner/FixedPartitioner.java

分区程序,确保每个内部Flink分区最终都在一个Kafka分区中。

通过完整的评论部分。他们也解释了各种情况。