1. 程式人生 > >Hadoop Yarn調度器的選擇和使用

Hadoop Yarn調度器的選擇和使用

容器 策略 admin 就是 HA username als 暫停 容量

一、引言

Yarn在Hadoop的生態系統中擔任了資源管理和任務調度的角色。在討論其構造器之前先簡單了解一下Yarn的架構。

技術分享圖片

上圖是Yarn的基本架構,其中ResourceManager是整個架構的核心組件,它負責整個集群中包括內存、CPU等資源的管理;ApplicationMaster負責應用程序在整個生命周期的任務調度;NodeManager負責本節點上資源的供給和隔離;Container可以抽象的看成是運行任務的一個容器。本文討論的調度器是在ResourceManager組建中進行調度的,接下來就一起研究一下包括FIFO調度器、Capacity調度器、Fair調度器在內的三個調度器。

二、FIFO調度器

技術分享圖片

上圖為FIFO調度器的執行過程示意圖。FIFO調度器也就是平時所說的先進先出(First In First Out)調度器。FIFO調度器是Hadoop最早應用的一種調度策略,可以簡單的將其理解為一個Java隊列,它的含義在於集群中同時只能有一個作業在運行。將所有的Application按照提交時候的順序來執行,只有當上一個Job執行完成之後後面的Job才會按照隊列的順序依次被執行。FIFO調度器以集群資源獨占的方式來運行作業,這樣的好處是一個作業可以充分利用所有的集群資源,但是對於運行時間短,重要性高或者交互式查詢類的MR作業就要等待排在序列前的作業完成才能被執行,這也就導致了如果有一個非常大的Job在運行,那麽後面的作業將會被阻塞。因此,雖然單一的FIFO調度實現簡單,但是對於很多實際的場景並不能滿足要求。這也就催發了Capacity調度器和Fair調度器的出現。

三、Capacity調度器

技術分享圖片

上圖是Capacity調度器的執行過程示意圖。Capacity調度器也就是日常說的容器調度器。可以將它理解成一個個的資源隊列。這個資源隊列是用戶自己去分配的。例如因為工作所需要把整個集群分成了AB兩個隊列,A隊列下面還可以繼續分,比如將A隊列再分為1和2兩個子隊列。那麽隊列的分配就可以參考下面的樹形結構:
—A[60%]
|—A.1[40%]
|—A.2[60%]
—B[40%]
上述的樹形結構可以理解為A隊列占用整個資源的60%,B隊列占用整個資源的40%。A隊列裏面又分了兩個子隊列,A.1占據40%,A.2占據60%,也就是說此時A.1和A.2分別占用A隊列的40%和60%的資源。雖然此時已經具體分配了集群的資源,但是並不是說A提交了任務之後只能使用它被分配到的60%的資源,而B隊列的40%的資源就處於空閑。只要是其它隊列中的資源處於空閑狀態,那麽有任務提交的隊列可以使用空閑隊列所分配到的資源,使用的多少是依據配來決定。參數的配置會在後文中提到。

在這裏還是要推薦下我自己建的大數據學習交流群:784557197,群裏都是學大數據開發的,如果你正在學習大數據 ,小編歡迎你加入,大家都是軟件開發黨,不定期分享幹貨(只有大數據軟件開發相關的),包括我自己整理的一份2018最新的大數據進階資料和高級開發教程,歡迎進階中和進想深入大數據的小夥伴加入。

Capacity調度器具有以下的幾個特性:

  • 層次化的隊列設計,這種層次化的隊列設計保證了子隊列可以使用父隊列設置的全部資源。這樣通過層次化的管理,更容易合理分配和限制資源的使用。
  • 容量保證,隊列上都會設置一個資源的占比,這樣可以保證每個隊列都不會占用整個集群的資源。
  • 安全,每個隊列又嚴格的訪問控制。用戶只能向自己的隊列裏面提交任務,而且不能修改或者訪問其他隊列的任務。
  • 彈性分配,空閑的資源可以被分配給任何隊列。當多個隊列出現爭用的時候,則會按照比例進行平衡。
  • 多租戶租用,通過隊列的容量限制,多個用戶就可以共享同一個集群,同事保證每個隊列分配到自己的容量,提高利用率。
  • 操作性,Yarn支持動態修改調整容量、權限等的分配,可以在運行時直接修改。還提供給管理員界面,來顯示當前的隊列狀況。管理員可以在運行時,添加一個隊列;但是不能刪除一個隊列。管理員還可以在運行時暫停某個隊列,這樣可以保證當前的隊列在執行過程中,集群不會接收其他的任務。如果一個隊列被設置成了stopped,那麽就不能向他或者子隊列上提交任務了。
  • 基於資源的調度,協調不同資源需求的應用程序,比如內存、CPU、磁盤等等。

相關參數的配置:

(1)capacity:隊列的資源容量(百分比)。 當系統非常繁忙時,應保證每個隊列的容量得到滿足,而如果每個隊列應用程序較少,可將剩余資源共享給其他隊列。註意,所有隊列的容量之和應小於100。
(2)maximum-capacity:隊列的資源使用上限(百分比)。由於存在資源共享,因此一個隊列使用的資源量可能超過其容量,而最多使用資源量可通過該參數限制。(這也是前文提到的關於有任務運行的隊列可以占用的資源的最大百分比)
(3)user-limit-factor:每個用戶最多可使用的資源量(百分比)。比如,假設該值為30,則任何時刻,每個用戶使用的資源量不能超過該隊列容量的30%。
(4)maximum-applications :集群或者隊列中同時處於等待和運行狀態的應用程序數目上限,這是一個強限制,一旦集群中應用程序數目超過該上限,後續提交的應用程序將被拒絕,默認值為 10000。所有隊列的數目上限可通過參數yarn.scheduler.capacity.maximum-applications設置(可看做默認值),而單個隊列可通過參數yarn.scheduler.capacity..maximum- applications設置適合自己的值。
(5)maximum-am-resource-percent:集群中用於運行應用程序 ApplicationMaster的資源比例上限,該參數通常用於限制處於活動狀態的應用程序數目。該參數類型為浮點型,默認是0.1,表示10%。所有隊列的ApplicationMaster資源比例上限可通過參數yarn.scheduler.capacity. maximum-am-resource-percent設置(可看做默認值),而單個隊列可通過參數 yarn.scheduler.capacity.. maximum-am-resource-percent設置適合自己的值。
(6)state :隊列狀態可以為STOPPED或者 RUNNING,如果一個隊列處於STOPPED狀態,用戶不可以將應用程序提交到該隊列或者它的子隊列中,類似的,如果ROOT隊列處於STOPPED 狀態,用戶不可以向集群中提交應用程序,但正在運行的應用程序仍可以正常運行結束,以便隊列可以優雅地退出。
(7)acl_submit_applications:限定哪些Linux用戶/用戶組可向給定隊列中提交應用程序。需要註意的是,該屬性具有繼承性,即如果一個用戶可以向某個隊列中提交應用程序,則它可以向它的所有子隊列中提交應用程序。配置該屬性時,用戶之間或用戶組之間用“,”分割,用戶和用戶組之間用空格分割,比如“user1, user2 group1,group2”。
(8)acl_administer_queue:為隊列指定一個管理員,該管理員可控制該隊列的所有應用程序,比如殺死任意一個應用程序等。同樣,該屬性具有繼承性,如果一個用戶可以向某個隊列中提交應用程序,則它可以向它的所有子隊列中提交應用程序。

四、Fair調度器

技術分享圖片

上圖是Fair調度器在一個隊列中的執行過程示意圖。Fair調度器也就是日常說的公平調度器。Fair調度器是一個隊列資源分配方式,在整個時間線上,所有的Job平均的獲取資源。默認情況下,Fair調度器只是對內存資源做公平的調度和分配。當集群中只有一個任務在運行時,那麽此任務會占用整個集群的資源。當其他的任務提交後,那些釋放的資源將會被分配給新的Job,所以每個任務最終都能獲取幾乎一樣多的資源。
技術分享圖片

公平調度器也可以在多個隊列間工作,如上圖所示,例如有兩個用戶A和B,他們分別擁有一個隊列。當A啟動一個Job而B沒有任務提交時,A會獲得全部集群資源;當B啟動一個Job後,A的任務會繼續運行,不過隊列A會慢慢釋放它的一些資源,一會兒之後兩個任務會各自獲得一半的集群資源。如果此時B再啟動第二個Job並且其它任務也還在運行時,那麽它將會和B隊列中的的第一個Job共享隊列B的資源,也就是隊列B的兩個Job會分別使用集群四分之一的資源,而隊列A的Job仍然會使用集群一半的資源,結果就是集群的資源最終在兩個用戶之間平等的共享。  

相關參數的配置:

(1)yarn.scheduler.fair.allocation.file: “allocation”文件的位置,“allocation”文件是一個用來描述queue以及它們的屬性的配置文件。這個文件必須為格式嚴格的xml文件。如果為相對路徑,那麽將會在classpath下查找此文件(conf目錄下)。默認值為“fair-scheduler.xml”。
(2)yarn.scheduler.fair.user-as-default-queue:是否將與allocation有關的username作為默認的queue name,當queue name沒有指定的時候。如果設置成false(且沒有指定queue name) 或者沒有設定,所有的jobs將共享“default” queue。默認值為true。
(3)yarn.scheduler.fair.preemption:是否使用“preemption”(優先權,搶占),默認為fasle,在此版本中此功能為測試性的。
(4)yarn.scheduler.fair.assignmultiple:是在允許在一個心跳中,發送多個container分配信息。默認值為false。
(5)yarn.scheduler.fair.max.assign:如果assignmultuple為true,那麽在一次心跳中,最多發送分配container的個數。默認為-1,無限制。
(6)yarn.scheduler.fair.locality.threshold.node:一個float值,在0~1之間,表示在等待獲取滿足node-local條件的containers時,最多放棄不滿足node-local的container的機會次數,放棄的nodes個數為集群的大小的比例。默認值為-1.0表示不放棄任何調度的機會。
(7)yarn.scheduler.fair.locality.threashod.rack:同上,滿足rack-local。
(8)yarn.scheduler.fair.sizebaseweight:是否根據application的大小(Job的個數)作為權重。默認為false,如果為true,那麽復雜的application將獲取更多的資源。

五、總結

如果業務邏輯比較簡單或者剛接觸Hadoop的時候建議使用FIFO調度器;如果需要控制部分應用的優先級同時又想要充分利用集群資源的情況下,建議使用Capacity調度器;如果想要多用戶或者多隊列公平的共享集群資源,那麽就選用Fair調度器。希望大家能夠根據業務所需選擇合適的調度器。

Hadoop Yarn調度器的選擇和使用