Spark性能調優之數據本地化

    本篇blog講述實際spark項目中調優的一個小技巧,調節數據本地化的等待時長。

    Spark在Driver上,對Application的每一個stage的task,進行分配之前,都會計算出每個task要計算的是哪個分片數據,RDD的某個partition;Spark的task分配算法,優先,會希望每個task正好分配到它要計算的數據所在的節點,這樣的話,就不用在網絡間傳輸數據;

     但是呢,通常來說,有時,事與願違,可能task沒有機會分配到它的數據所在的節點,爲什麼呢,可能那個節點的計算資源和計算能力都滿了;所以呢,這種時候,通常來說,Spark會等待一段時間,默認情況下是3s鍾(不是絕對的,還有很多種情況,對不同的本地化級別,都會去等待),到最後,實在是等待不了了,就會選擇一個比較差的本地化級別,比如說,將task分配到靠它要計算的數據所在節點,比較近的一個節點,然後進行計算。

    但是對於第二種情況,通常來說,肯定是要發生數據傳輸,task會通過其所在節點的BlockManager來獲取數據,BlockManager發現自己本地沒有數據,會通過一個getRemote()方法,通過TransferService(網絡數據傳輸組件)從數據所在節點的BlockManager中,獲取數據,通過網絡傳輸回task所在節點。


數據本地化的幾個級別:

PROCESS_LOCAL:進程本地化,代碼和數據在同一個進程中,也就是在同一個executor中;計算數據的task由executor執行,數據在executor的BlockManager中;性能最好

NODE_LOCAL:節點本地化,代碼和數據在同一個節點中;比如說,數據作爲一個HDFS block塊,就在節點上,而task在節點上某個executor中運行;或者是,數據和task在一個節點上的不同executor中;數據需要在進程間進行傳輸

NO_PREF:對於task來說,數據從哪裏獲取都一樣,沒有好壞之分

RACK_LOCAL:機架本地化,數據和task在一個機架的兩個節點上;數據需要通過網絡在節點之間進行傳輸

ANY:數據和task可能在集羣中的任何地方,而且不在一個機架中,性能最差


如何調節參數?

觀察日誌,推薦先用client模式,在本地可以看到比較全的spark作業的運行日誌。日誌會顯示,starting task。。。,PROCESS LOCAL、NODE LOCAL觀察大部分task的數據本地化級別。

1.如果大多都是PROCESS_LOCAL,那就不用調節了

2.如果大多都是NODE_LOCAL、ANY,那麼最好就去調節一下數據本地化的等待時長

調節完,應該是要反覆調節,每次調節完以後,再來運行,觀察日誌

3.反覆調節看看大部分的task的本地化級別有沒有提升;注意平衡等待時間和計算時間,看整個spark作業的運行時間有沒有縮短

new SparkConf().set("spark.locality.wait","10")













發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章