Spark2.1.0模型設計與基本架構(下)
閱讀提示:讀者如果對Spark的背景知識不是很瞭解的話,建議首先閱讀《SPARK2.1.0模型設計與基本架構(上)》一文。
Spark模型設計
1. Spark程式設計模型
正如Hadoop在介紹MapReduce程式設計模型時選擇word count的例子,並且使用圖形來說明一樣,筆者對於Spark程式設計模型也選擇用圖形展現。
Spark 應用程式從編寫到提交、執行、輸出的整個過程如圖5所示。
圖5 程式碼執行過程
圖5中描述了Spark程式設計模型的關鍵環節的步驟如下。
1)使用者使用SparkContext提供的API(常用的有textFile、sequenceFile、runJob、stop等)編寫Driver application程式。此外,SparkSession、DataFrame、SQLContext、HiveContext及StreamingContext都對SparkContext進行了封裝,並提供了DataFrame、SQL、Hive及流式計算相關的API。
2)使用SparkContext提交的使用者應用程式,首先會通過RpcEnv向叢集管理器(Cluster Manager)註冊應用(Application)並且告知叢集管理器需要的資源數量。叢集管理器根據Application的需求,給Application分配Executor資源,並在Worker上啟動CoarseGrainedExecutorBackend程序(CoarseGrainedExecutorBackend程序內部將建立Executor)。Executor所在的CoarseGrainedExecutorBackend程序在啟動的過程中將通過RpcEnv直接向Driver註冊Executor的資源資訊,TaskScheduler將儲存已經分配給應用的Executor資源的地址、大小等相關資訊。然後,SparkContext根據各種轉換API,構建RDD之間的血緣關係(lineage)和DAG,RDD構成的DAG將最終提交給DAGScheduler。DAGScheduler給提交的DAG建立Job並根據RDD的依賴性質將DAG劃分為不同的Stage。DAGScheduler根據Stage內RDD的Partition數量建立多個Task並批量提交給TaskScheduler。TaskScheduler對批量的Task按照FIFO或FAIR排程演算法進行排程,然後給Task分配Executor資源,最後將Task傳送給Executor由Executor執行。此外,SparkContext還會在RDD轉換開始之前使用BlockManager和BroadcastManager將任務的Hadoop配置進行廣播。
3)叢集管理器(Cluster Manager)會根據應用的需求,給應用分配資源,即將具體任務分配到不同Worker節點上的多個Executor來處理任務的執行。Standalone、YARN、Mesos、EC2等都可以作為Spark的叢集管理器。
4)Task在執行的過程中需要對一些資料(例如中間結果、檢查點等)進行持久化,Spark支援選擇HDFS 、Amazon S3、Alluxio(原名叫Tachyon)等作為儲存。
2.RDD計算模型
RDD可以看做是對各種資料計算模型的統一抽象,Spark的計算過程主要是RDD的迭代計算過程,如圖6所示。RDD的迭代計算過程非常類似於管道。分割槽數量取決於Partition數量的設定,每個分割槽的資料只會在一個Task中計算。所有分割槽可以在多個機器節點的Executor上並行執行。
圖6 RDD計算模型
圖6只是簡單的從分割槽的角度將RDD的計算看作是管道,如果從RDD的血緣關係、Stage劃分的角度來看,由RDD構成的DAG經過DAGScheduler排程後,將變成圖7所示的樣子。
圖7 DAGScheduler對由RDD構成的DAG進行排程
圖7中共展示了A、B、C、D、E、F、G一共7個RDD。每個RDD中的小方塊代表一個分割槽,將會有一個Task處理此分割槽的資料。RDD A經過groupByKey轉換後得到RDD B。RDD C經過map轉換後得到RDD D。RDD D和RDD E經過union轉換後得到RDD F。RDD B和RDD F經過join轉換後得到RDD G。從圖中可以看到map和union生成的RDD與其上游RDD之間的依賴是NarrowDependency,而groupByKey和join生成的RDD與其上游的RDD之間的依賴是ShuffleDependency。由於DAGScheduler按照ShuffleDependency作為Stage的劃分的依據,因此A被劃入了ShuffleMapStage 1;C、D、E、F被劃入了ShuffleMapStage 2;B和G被劃入了ResultStage 3。
Spark基本架構
從叢集部署的角度來看,Spark叢集由叢集管理器(Cluster Manager)、工作節點(Worker)、執行器(Executor)、驅動器(Driver)、應用程式(Application)等部分組成,它們之間的整體關係如圖8所示。
圖8 Spark基本架構圖
下面結合圖8對這些組成部分以及它們之間的關係進行介紹。
(1)Cluster Manager
Spark的叢集管理器,主要負責對整個叢集資源的分配與管理。Cluster Manager在Yarn部署模式下為ResourceManager;在Mesos部署模式下為Mesos master;在Standalone部署模式下為Master。Cluster Manager分配的資源屬於一級分配,它將各個Worker上的記憶體、CPU等資源分配給Application,但是並不負責對Executor的資源分配。Standalone部署模式下的Master會直接給Application分配記憶體、CPU以及Executor等資源。目前,Standalone、YARN、Mesos、EC2等都可以作為Spark的叢集管理器。
注意:這裡提到了部署模式中的Standalone、Yarn、Mesos等模式,讀者暫時知道這些內容即可,本書將在第9章對它們詳細介紹。
(2)Worker
Spark的工作節點。在Yarn部署模式下實際由NodeManager替代。Worker節點主要負責以下工作:將自己的記憶體、CPU等資源通過註冊機制告知Cluster Manager;建立Executor;將資源和任務進一步分配給Executor;同步資源資訊、Executor狀態資訊給Cluster Manager等。在Standalone部署模式下,Master將Worker上的記憶體、CPU以及Executor等資源分配給Application後,將命令Worker啟動CoarseGrainedExecutorBackend程序(此程序會建立Executor例項)。
(3)Executor
執行計算任務的一線元件。主要負責任務的執行以及與Worker、Driver的資訊同步。
(4)Driver
Application的驅動程式,Application通過Driver與Cluster Manager、Executor進行通訊。Driver可以執行在Application中,也可以由Application提交給Cluster Manager並由Cluster Manager安排Worker執行。
(4)Application
使用者使用Spark提供的API編寫的應用程式,Application通過Spark API將進行RDD的轉換和DAG的構建,並通過Driver將Application註冊到Cluster Manager。Cluster Manager將會根據Application的資源需求,通過一級分配將Executor、記憶體、CPU等資源分配給Application。Driver通過二級分配將Executor等資源分配給每一個任務,Application最後通過Driver告訴Executor執行任務。
小結
每項技術的誕生都會由某種社會需求所驅動,Spark正是在實時計算的大量需求下誕生的。Spark藉助其優秀的處理能力,可用性高,豐富的資料來源支援等特點,在當前大資料領域變得火熱,參與的開發者也越來越多。Spark經過幾年的迭代發展,如今已經提供了豐富的功能。筆者相信,Spark在未來必將產生更耀眼的火花。
關於《Spark核心設計的藝術 架構設計與實現》
經過近一年的準備,基於Spark2.1.0版本的《Spark核心設計的藝術 架構設計與實現》一書現已出版發行,圖書如圖:
紙質版售賣連結如下: