您的位置:首页 > 其它

SparkStreaming整合Kafka--之Receiver和直连方式介绍

2019-04-08 17:03 218 查看

配置Spark Streaming以从Kafka接收数据,有两种方法 :
1.使用Receivers和Kafka的高级API的旧方法。
2.不使用Receiver的新方法(在Spark 1.3中引入,就是直连方式)。

它们具有不同的编程模型,性能特征。

Receiver

此方法使用Receiver接收数据。Receiver是使用Kafka高级消费者API实现的。与所有接收器一样,从Kafka通过Receiver接收的数据存储在Spark执行器(executor)中,然后由Spark Streaming启动的job处理数据。

但是,在默认配置下,此方法可能会在失败时丢失数据(为确保零数据丢失,您必须在Spark Streaming中另外启用预写日志(在Spark 1.2中引入)。这将同步保存所有收到的Kafka将数据转换为分布式文件系统(例如HDFS)上的预写日志,以便在发生故障时可以恢复所有数据。

这种方式中,Driver生成jobs交给executor端执行,executor接收到任务后,每个一定的时间从Kafka中拉去数据,拉取完这个时间段的数据之后才开始执行,但是此时有一个问题,如果某个时间段产生的数据特别多的话,他就会把多余的数据(内存装不下的数据)写入到磁盘中。这种方式使用zookeeper来记录偏移量。

缺点:Receiver接收固定时间间隔的数据(放在内存中),使用Kafka高级的API,自动维护偏移量,省事,数据达到固定的时间才进行处理,效率低并且容易丢失数据。

所以Receiver这种方式在Kafka0.10版本之后就不再使用了。

直连方式

Spark 1.3中引入了这种新的无接收器“直接”方法,以确保更强大的端到端保证。这种方法不是使用接收器来接收数据,而是定期向Kafka查询每个主题+分区中的最新偏移量,并相应地定义要在每个批次中处理的偏移量范围。当启动处理数据的作业时,Kafka的简单消费者API用于从Kafka读取定义的偏移范围(类似于从文件系统读取的文件)。请注意,此功能是在Spark 1.3中为Scala和Java API引入的,在Python 1.4中为Python API引入。

与基于接收器的方法(即Receiver)相比,该方法具有以下优点:

1.简化的并行性:无需创建多个输入Kafka流并将它们联合起来。使用directStream,Spark Streaming将创建与要使用的Kafka分区一样多的RDD分区,这些分区将并行地从Kafka读取数据。因此,Kafka和RDD分区之间存在一对一的映射,这更容易理解和调整。

2.效率:在Receiver中要实现零数据丢失就需要将数据存储在预写日志中,这会进一步复制数据。这实际上是低效的,因为数据有效地被复制两次 , 一次由Kafka复制,第二次由Write-Ahead Log复制。第二种方法避免了这个问题,因为没有接收器,因此不需要预写日志。只要您有足够的Kafka保留,就可以从Kafka中恢复消息。

3.只有一次语义:第一种方法使用Kafka的高级API在Zookeeper中存储消耗的偏移量。传统上,这是从Kafka使用数据的方式。虽然这种方法(与预写日志结合使用)可以确保零数据丢失(即至少一次语义),但某些记录在某些故障下可能会被消耗两次。这是因为Spark Streaming可靠接收的数据与Zookeeper跟踪的偏移之间存在不一致。因此,在第二种方法中,我们不使用Zookeeper的简单Kafka API。Spark Streaming在其检查点内跟踪偏移量。这消除了Spark Streaming和Zookeeper / Kafka之间的不一致,因此尽管出现故障,Spark Streaming也会有效地接收每条记录一次。


Driver首先会从Kafka中查询偏移量,如果之前已经读取过(处理过)数据了,那么就接着读取,如果没有读取过数据,就从头开始读。这个偏移量数据可以保存到外部存储系统中,比如Redis,zookeeper中。
然后Driver启动任务,交给executor执行,executor直接连接到Kafka的分区中,executor中的Task一直从Kafka中读取数据。

Direct直连方式,相当于直接连接到Kafka的分区上,使用Kafka底层的API,效率高,但是需要自己维护偏移量。

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: