SparkStreaming消費kafka中數據的方式


有兩種:Direct直連方式、Receiver方式

1、Receiver方式:

(1)receiver內存溢出問題:

  使用kafka高層次的consumer API來實現,使用receiver從kafka中獲取的數據都保存在spark excutor的內存中,然后由Spark Streaming啟動的job來處理數據。因此一旦數據量暴增,很容易造成內存溢出。

(2)數據丟失:

  並且,在默認配置下,這種方式可能會因為底層失敗而造成數據丟失,如果要啟用高可靠機制,確保零數據丟失,要啟用Spark Streaming的預寫日志機制(Write Ahead Log,(已引入)在Spark 1.2)。該機制會同步地將接收到的Kafka數據保存到分布式文件系統(比如HDFS)上的預寫日志中,以便底層節點在發生故障時也可以使用預寫日志中的數據進行恢復。

(3)數據重復消費:

  使用 Kafka 的高階 API來在 ZooKeeper 中保存消費過的 offset的。這是消費 Kafka 數據的傳統方式。這種方式配合着 WAL機制可以保證數據零丟失的高可靠性,但是卻無法保證數據被處理一次且僅一次,可能會處理兩次。因為 Spark和ZooKeeper之間可能是不同步的。

 

 2、Direct直連方式:

  這種新的不基於 Receiver 的直接方式,是在 Spark 1.3 中引入的。替代掉使用 Receiver 來接收數據后,這種方式會周期性地查詢 Kafka,來獲得每個 topic+partition 的最新的 offset,從而定義每個 batch 的 offset 的范圍。當處理數據的job 啟動時,就會使用 Kafka 的簡單 consumer api 來獲取 Kafka 指定 offset范圍的數據

  使用 kafka 的簡單 api,Spark Streaming 自己就負責追蹤消費的offset,並保存在 checkpoint中。Spark自己一定是同步的,因此可以保證數據是消費一次且僅消費一次。

 

這種方法相較於Receiver方式的優勢在於:

  • 簡化的並行:在Receiver的方式中我們提到創建多個Receiver之后利用union來合並成一個Dstream的方式提高數據傳輸並行度。而在Direct方式中,Kafka中的partition與RDD中的partition是一一對應的並行讀取Kafka數據,這種映射關系也更利於理解和優化。
  • 高效:在Receiver的方式中,為了達到0數據丟失需要將數據存入Write Ahead Log中,這樣在Kafka和日志中就保存了兩份數據,浪費!而第二種方式不存在這個問題,只要我們Kafka的數據保留時間足夠長,我們都能夠從Kafka進行數據恢復。
  • 精確一次:在Receiver的方式中,使用的是Kafka的高階API接口從Zookeeper中獲取offset值,這也是傳統的從Kafka中讀取數據的方式,但由於Spark Streaming消費的數據和Zookeeper中記錄的offset不同步,這種方式偶爾會造成數據重復消費。而第二種方式,直接使用了簡單的低階Kafka API,Offsets則利用Spark Streaming的checkpoints進行記錄,消除了這種不一致性。

請注意,此方法的一個缺點是它不會更新Zookeeper中的偏移量,因此基於Zookeeper的Kafka監視工具將不會顯示進度。但是,您可以在每個批處理中訪問此方法處理的偏移量,並自行更新Zookeeper。

 

參考博客:https://www.cnblogs.com/frankdeng/p/9308585.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM