我创建了以下代码,它创建了6个输入DStream,它使用直接aproach从Kafka读取6个分区主题,我发现即使为流指定相同的组ID,我也会重复6次数据。如果我只创建3个DStreams,我会重复数据3次等等......
numStreams = 6
kafkaStreams = [KafkaUtils.createDirectStream(ssc, ["send6partitions"], {
"metadata.broker.list": brokers,
"fetch.message.max.bytes": "20971520",
"spark.streaming.blockInterval" : "2000ms",
"group.id" : "the-same"},
valueDecoder = decodeValue, keyDecoder = decode_key) for _ in range (numStreams)]
kvs = ssc.union(*kafkaStreams)
我在这里做错了什么?
答案 0 :(得分:1)
我不熟悉Python,但Spark Scala中的Direct Stream不提交任何偏移。因此,如果您打开一个流n次而不提交任何读取消息的偏移量,您的消费者将从头开始。
如果在python中相同,则不需要启动n个流。启动一个流,Spark将处理分区到执行程序/任务本身的分配。
答案 1 :(得分:1)
在Direct方法中,你不应该从一个主题创建许多DStream。
简化并行:无需创建多个输入Kafka流 并结合他们。使用directStream,Spark Streaming将创建尽可能多的内容 RDD分区,因为有Kafka分区要使用,这将是 所有人都从Kafka并行读取数据。所以有一对一的映射 在Kafka和RDD分区之间,这更容易理解和 调。
所以只需创建一个DStream,Spark就会使用所有Kafka分区:)
答案 2 :(得分:1)
基本上,通过共享负载,Kafka主题可以分配给多个接收者/消费者更快的分发。默认情况下,当您创建Dstream时,一个接收者将通过接收者线程并行地运行和接收来自每个Kafka主题分区到Dstream分区的数据(Java)线)。如果要为一个主题创建6个Dstream,则表示同一主题的6个接收器并不意味着每个端口的每个Dstream。每个接收器一次获得每个馈送,因此每次馈送获得6次。