上一篇講到Yarn是什麼?講到這,咱們知道其有哪些調度方式嗎?html
YARN之三種調度方式:node
下面主要講CapacityScheduler實現邏輯:算法
1、應用程序初始化apache
應用程序被提交到ResourceManager以後,ResourceManager會向Capacity Scheduler發送一個SchedulerEventType.APP_ADDED事件,Capacity Scheduler收到該事件後,將爲應用程序建立一個FiCaSchedulerApp對象跟蹤和維護該應用程序的運行時信息,同時將應用程序提交到對應的葉子隊列中,葉子隊列會對應用程序進行一系列檢查,包括如下幾個方面:安全
1. 應用程序所屬用戶擁有該葉子隊列的應用程序提交權限服務器
2. 隊列及其父隊列當前處於RUNNING狀態(遞歸檢查)微信
3. 隊列當前已提交的應用程序數目未達到管理員設定的上限數據結構
4. 應用程序所屬用戶提交的應用程序數目未超過管理員設定的上限併發
2、資源調度app
當ResourceManager收到來自NodeManager發送的心跳信息後,將向Capacity Scheduler發送一個SchedulerEventType.NODE_UPDATE事件,Capacity Scheduler收到該事件後,會依次進行如下操做:
1. 處理心跳信息:NodeManager發送的心跳信息中有兩類信息需資源調度器處理,一類是最新啓動的Container,另外一類是運行完成的Container,具體以下:
對於最新啓動的Container,資源調度器需向ResourceManager發送一個RMContainerEventType.LAUNCHED,進而將該Container從超時監控隊列中刪除。當資源調度器爲ApplicationMaster分配一個Container後,爲了防止ApplicationMaster長時間不使用該Container形成資源浪費,它會將該Container加入一個超時監控隊列中。若是一段時間內,該隊列中的Container仍未被使用,則資源調度器會回收該Container。
對於運行完成的Container,資源管理器將回收它使用的資源,以便接下來對這些資源進行再分配。
處理完以上兩類信息後,Capacity Scheduler將節點上的空閒資源分配給應用程序。
2. 資源分配:
從根隊列開始,使用深度優先遍歷算法,從根隊列開始,依次遍歷子隊列找出資源使用率最小的子隊列。若子隊列爲葉子隊列,則選擇該隊列,從而進行step二、step3;若子隊列爲非葉子隊列,則以該子隊列爲根隊列重複前面的過程直到找到一個資源使用率最小的葉子隊列爲止。
注意:上述「隊列資源使用率」計算方法爲已經使用的資源量除以最小隊列資源容量(由管理員配置)。對於非葉子隊列,它的已使 用資源量是各個子隊列已使用資源量之和。
在Step1中選好了葉子隊列後,取該隊列中最先提交的應用程序(實際排序時用的 Application ID,提交時間越早的應用程序,Application ID 越小)。
(5). 其餘事件處理
CS資源分配流程:
Step1:選擇隊列
Step2:選擇應用
Step3:選擇 Container
YARN請求資源時的locality和relaxility限定:
CS分配資源過程:
CS中配置:
yarn.scheduler.capacity.maximum-am-resource-percent #設置有多少資源能夠用來運行app master,即控制當前激活狀態的應用:100%
yarn.scheduler.capacity.maximum-applications #設置系統中能夠同時運行和等待的應用數量:10000
yarn.scheduler.capacity.root.queues #子對列:default, vc1
yarn.scheduler.capacity.root.default.capacity #它是隊列的資源容量佔比(百分比)。系統繁忙時,每一個隊列都應該獲得設置的量的資源;當系統空閒時,該隊列的資源則能夠被其餘的隊列使用。同一層的全部隊列加起來必須是100%。
yarn.scheduler.capacity.root.default.maximum-capacity #隊列資源的使用上限。因爲系統空閒時,隊列可使用其餘的空閒資源,所以最多使用的資源量則是該參數控制。默認是-1,即禁用。
yarn.scheduler.capacity.root.default.user-limit-factor #能夠配置爲容許單個用戶獲取更多資源的隊列容量的倍數。默認是1,這能夠確保不管集羣有多空閒,單個用戶都不能佔用超過隊列配置的容量。值被指定爲浮點。
每一個用戶最多使用的隊列資源佔比
yarn.scheduler.capacity.root.default.minimum-user-limit-percent #若是對資源有需求,每一個隊列都強制限制在任何給定時間分配給用戶的資源百分比。用戶限制能夠在最小值和最大值之間變化。前者(最小值)設置爲該屬性值,後者(最大值)取決於已提交應用程序的用戶數。例如,假設該屬性的值爲25。若是兩個用戶向一個隊列提交了應用程序,則任何一個用戶都不能使用超過50%的隊列資源。若是第三個用戶提交了一個應用程序,那麼任何一個用戶都不能使用超過33%的隊列資源。對於4個或更多用戶,沒有任何用戶可使用超過25%的隊列資源。值爲100表示不施加用戶限制。默認值爲100。值被指定爲整數。
yarn.scheduler.maximum-allocation-vcores #每一個隊列對Resource Manager申請的每個容器分配虛擬計算核的最大限制。
yarn.scheduler.maximum-allocation-gpus #每一個隊列對Resource Manager申請的每個容器分配gpu的最大限制。
yarn.resourcemanager.connect.retry-interval.ms #rm失聯後從新連接的時間: 1000ms 。
yarn.scheduler.capacity.<queue-path>.user-settings.<user-name>.weight #此浮點值用於計算隊列中用戶的用戶限制資源值。該值將使每一個用戶的權重大於或小於隊列中的其餘用戶。例如,若是用戶A在隊列中收到的資源比用戶B和C多50%,則用戶A的此屬性將設置爲1.5。用戶B和C將默認爲1.0。
yarn.scheduler.capacity.<queue-path>.maximum-application-lifetime #提交到隊列的應用程序的最長生存時間(秒)。任何小於或等於零的值都將被視爲禁用。對於此隊列中的全部應用程序,這將是一個困難的時間限制。若是配置了正值,則提交到此隊列的任何應用程序都將在超過配置的生存期後終止。用戶還能夠在應用程序提交上下文中爲每一個應用程序指定生存期。可是,若是用戶生存期超過了隊列的最大生存期,那麼它將被覆蓋。它是時間點配置。注意:配置過低的值將致使更快地終止應用程序。此功能僅適用於葉隊列。
yarn.scheduler.capacity.root.<queue-path>.default-application-lifetime #提交到隊列的應用程序的默認生存期(秒)。任何小於或等於零的值都將被視爲禁用。若是用戶未提交生存期值爲的應用程序,則將採用此值。它是時間點配置。注意:默認生存期不能超過最大生存期。此功能僅適用於葉隊列。
yarn.scheduler.capacity.node-locality-delay:40 #表示調度器在放鬆節點限制、改成匹配同一機架上的其餘節點前嘗試錯過的調度機會數。一般,應該將其設置爲集羣中的節點數。默認狀況下,在一個機架中設置大約40個節點。應爲正整數值。
yarn.scheduler.capacity.resource-calculator #有兩種比較器用以比較兩個資源的大小(好比比較用戶當前使用的資源量是否超過了設置的上限資源量),默認是DefaultResourceCalculator,它只考慮Memory資源。另一種是DominantResourceCalculator,它採用了DRF比較算法,同時考慮Memory和CPU兩種資源。
yarn.scheduler.capacity.<queue-path>.state #隊列的狀態。能夠是正在運行或已中止。若是隊列處於已中止狀態,則沒法將新應用程序提交到其自身或其任何子隊列。所以,若是根隊列被中止,就不能向整個集羣提交任何應用程序。現有的應用程序繼續完成,所以能夠適當地排出隊列。值被指定爲枚舉。
yarn.scheduler.capacity.root.<queue-path>.acl_submit_applications:限定哪些用戶/用戶組可向給定隊列中提交應用程序。該屬性具備繼承性,即若是一個用戶能夠向某個隊列提交應用程序,則它能夠向它全部子隊列中提交應用程序。
yarn.scheduler.capacity.root.<queue-path>.acl_administer_queue #爲隊列指定一個管理員,該管理員可控制該隊列的全部應用程序,好比殺死任意一個應用程序等。一樣,該屬性具備繼承性,若是一個用戶能夠向某個隊列中提交應用程序,則它能夠向它的全部子隊列中提交應用程序。
yarn.scheduler.capacity.root.<queue>.acl_administer_reservations #ACL控制誰能夠管理指定的隊列的保留資源。若是不指定,則對於這個屬性的ACL不會從父隊列繼承。
yarn.scheduler.capacity.root.<queue>.acl_list_reservations #ACL控制誰能夠列出指定隊列的保留資源。若是不指定,則對於這個屬性的ACL不會從父隊列繼承。
yarn.scheduler.capacity.root.<queue>.acl_submit_reservations #ACL控制誰能夠提交保留資源到指定的隊列。若是不指定,則對於這個屬性的ACL不會從父隊列繼承。
yarn.scheduler.capacity.schedule-asynchronously.enable:是否開啓異步調度 默認false
yarn.scheduler.capacity.schedule-asynchronously.scheduling-interval-ms:異步調度間隔 --- 5
yarn.scheduler.capacity.schedule-asynchronously.maximum-threads:開啓異步調度最大線程數
yarn.scheduler.capacity.per-node-heartbeat.multiple-assignments-enabled:是否容許在一個節點管理器心跳中分配多個容器 true
yarn.scheduler.capacity.lazy-preemption-enabled:false 是否開啓懶搶佔 CapacitySchedulerConfiguration類
yarn.scheduler.capacity.per-node-heartbeat.maximum-container-assignments:若是啓用了多個分配,則一個節點能夠分配的最大容器數。默認爲-1,不設置限制。
yarn.scheduler.capacity.maximum-am-resource-percent:羣集中可用於運行應用程序主控形狀的最大資源百分比-控制併發活動應用程序的數量。每一個隊列的限制與其隊列容量和用戶限制成正比。默認值爲0.1。
yarn.scheduler.capacity.per-node-heartbeat.maximum-offswitch-assignments:若是啓用了多個分配,控制節點心跳期間容許的OFF_SWITCH分配的數量
yarn.scheduler.capacity.queue-mappings-override.enable:此函數用於指定是否能夠覆蓋用戶指定的隊列。默認值爲false mapreduce.job.queuename
yarn.scheduler.capacity.rack-locality-additional-delay:在節點本地延遲時間以外的另外的錯過的調度機會的次數,在此以後,CapacityScheduler嘗試調度非切換容器而不是機架本地容器.例如:在node-locality-delay = 40和rack-locality-delay = 20的狀況下,調度器將在40次錯過機會以後嘗試機架本地分配,在40 + 20 = 60以後錯過機會.使用-1做爲默認值,禁用此功能. 在這種狀況下,根據資源請求中指定的容器和惟一位置的數量以及集羣的大小,計算分配關閉交換容器的錯失機會的數量
yarn.scheduler.capacity.root.<leaf-queue-path>.default-application-priority:定義葉隊列中的默認應用程序優先級。默認0,最高,邏輯控制
yarn.cluster.max-application-priority:定義集羣中最大應用的優先級
yarn.scheduler.capacity.root.<queue_name>.<priority>.acl=user1,user2 #隊列的acl用戶
具體參考:http://hadoop.apache.org/docs/current/hadoop-yarn/hadoop-yarn-site/CapacityScheduler.html
隊列容量=yarn.scheduler.capacity.<queue-path>.capacity/100 --90
隊列絕對容量=父隊列的 隊列絕對容量*隊列容量 ---1 * 90%
隊列最大容量=yarn.scheduler.capacity.<queue-path>.maximum-capacity/100 ---90%
隊列絕對最大容量=父隊列的 隊列絕對最大容量*隊列最大容量 ---90%
絕對資源使用比=使用的資源/全局資源
資源使用比=使用的資源/(全局資源 * 隊列絕對容量)
最小分配量=yarn.scheduler.minimum-allocation-mb ---邏輯控制
用戶上限=MAX(yarn.scheduler.capacity.<queue-path>.minimum-user-limit-percent,1/隊列用戶數量)
用戶調整因子=yarn.scheduler.capacity.<queue-path>.user-limit-factor,容許單個用戶獲取更多資源的隊列容量的倍數
最大提交應用=yarn.scheduler.capacity.<queue-path>.maximum-applications,若是小於0 設置爲(yarn.scheduler.capacity.maximum-applications*隊列絕對容量)
單用戶最大提交應用=最大提交應用*(用戶上限/100)*用戶調整因子
AM資源佔比(AM可佔用隊列資源最大的百分比) =yarn.scheduler.capacity.<queue-path>.maximum-am-resource-percent,若是爲空,設置爲yarn.scheduler.capacity.maximum-am-resource-percent
最大活躍應用數量=全局總資源/最小分配量*AM資源佔比*隊列絕對最大容量
單用戶最大活躍應用數量=(全局總資源/最小分配量*AM資源佔比*隊列絕對容量)*用戶上限*用戶調整因子
本地延遲分配次數=yarn.scheduler.capacity.node-locality-delay
枚舉:
USED_CAP(0),
ABS_USED_CAP(1), 絕對容量
MAX_CAP(2),
ABS_MAX_CAP(3),絕對最大容量
CAP(4),
ABS_CAP(5),
MAX_AM_PERC(6),
RESERVED_CAP(7),預留容量
ABS_RESERVED_CAP(8);絕對預留容量
CS中標籤的概念:
什麼是Node-label
Node-label特性
1. 只適用於Capacity Scheduler,不支持Fair Scheduler
2. 一個Node Manager節點只能屬於一個label,若是一個資源節點沒有配置label,則其屬於一個不存在的DEFAULT分區【即沒有被設置label的節點】,沒有指定隊列的做業將會被放置到這些節點上運行,若是全部節點被設置label,沒有指定隊列的將會中止在accepted節點,後續將由於得不到資源而failed
3. 用戶能夠爲每一個隊列配置能夠訪問的分區【label】,默認是隻能夠訪問DEFAULT分區
4. 若是隊列配置爲對全部label可訪問,該隊列上的做業可使用全部label節點上的資源
5. 能夠設置每一個隊列訪問特定分區的資源比率
6. node label以及隊列和node label的相關配置支持動態更新----便可使用yarn rmadmin –replaceLabelsOnNode 修改節點標籤
Reservation概念:
爲了解決Queue被一個須要不少資源的Application霸佔。咱們能夠經過Reservation先保留一部分資源,分配給其餘的高優先級的容器。這就是它的做用。可是須要注意的是,每臺NodeManager只能對應一個Reservation.
yarn.resourcemanager.reservation-system.enable:必須指定的參數。默認值爲false。
yarn.resourcemanager.reservation-system.class:可選參數。默認值取決於調度器,若是是容量調度器,則爲CapacityReservationSystem。
yarn.resourcemanager.reservation-system.plan.follower:可選參數。基於調度器,CapacitySchedulerPlanFollower,經過動態的建立/調整/銷燬隊列,將計劃狀態發佈到調度程序。
yarn.resourcemanager.reservation-system.planfollower.time-step:可選參數。默認值爲1000ms。PlanFollower計時器的頻率ReservationSystem能夠被配置到任何隊列,包括葉子隊列。
yarn.scheduler.capacity.<queue-path>.reservable:必須指定的參數。代表隊列的資源對於用戶保留來講是可得到的。默認否false
yarn.scheduler.capacity.<queue-path>.reservation-agent:可選參數。將嘗試將用戶的預訂請求放入計劃中,默認值爲org.apache.hadoop.yarn.server.resourcemanager.reservation.planning.AlignedPlannerwithGreedy。
yarn.scheduler.capacity.<queue-path>.reservation-policy:可選參數。將用於肯定sharingpolicy(共享策略)實現的類名,它將驗證新保留是否不違反任何不變量。
org.apache.hadoop.yarn.server.resourcemanager.reservation.CapacityOverTimePolicy.
yarn.scheduler.capacity.<queue-path>.reservation-window:可選參數,表示若是知足計劃中的約束,sharingpolicy將驗證的時間(毫秒)。Long類型值,默認是一天。
yarn.scheduler.capacity.<queue-path>.instantaneous-max-capacity:可選參數,任什麼時候候的最大容量,默認爲1,即100%。
yarn.scheduler.capacity.<queue-path>.average-capacity:可選參數。將在ReservationWindow上聚合的平均容許容量,以百分比(%)表示,做爲sharingPolicy容許單個用戶保留的浮點值。默認100%。
yarn.scheduler.capacity.<queue-path>.reservation-planner:可選參數。計劃預留器實現的類,默認:org.apache.hadoop.yarn.server.resourcemanager.reservation.planning.SimpleCapacityReplanner。
yarn.scheduler.capacity.<queue-path>.reservation-enforcement-window:可選參數。表示計劃預留者驗證預留中約束是否知足的時間(毫秒)默認爲1小時。
yarn.scheduler.capacity.resource-calculator:資源計算方法,默認是org.apache.hadoop.yarn.util.resource.DefaultResourseCalculator,它只會計算內存。DominantResourceCalculator則會計算內存和CPU。
CS調度流程:
Capacity調度器說的通俗點,能夠理解成一個個的資源隊列。這個資源隊列是用戶本身去分配的。好比我大致上把整個集羣分紅了AB兩個隊列,A隊列給A項目組的人來使用。B隊列給B項目組來使用。可是A項目組下面又有兩個方向,那麼還能夠繼續分,好比專門作A一、A2的。
在正常的操做中,Capacity調度器不會強制釋放Container,當一個隊列資源不夠用時,這個隊列只能得到其它隊列釋放後的Container資源。固然,咱們能夠爲隊列設置一個最大資源使用量,以避免這個隊列過多的佔用空閒資源,致使其它隊列沒法使用這些空閒資源,這就是」彈性隊列」須要權衡的地方。
Root
--default 60%
--a 40%
--b 60%
--vc1 40%
--c
--d
Queue Elasticity:雖然有了這樣的資源分配,可是並非說default提交了任務,它就只能使用60%的資源,那40%就空閒着。只要資源處於空閒狀態,那麼default就可使用100%的資源。可是一旦vc1提交了任務,default就須要在釋放資源後,把資源還給vc1隊列,直到二者平衡在3:2的比例。
粗粒度上資源是按照上面的方式進行,在每一個隊列的內部,仍是按照FIFO的原則來分配資源的。
Capacity Scheduler資源調度器也採用層級隊列組織方式,其ROOT隊列能夠有多個子隊列,而每一個子隊列又能夠有本身的子隊列,在隊列層級最下面是葉子隊列,全部Application皆提交至葉子隊列。Capacity Scheduler以隊列爲單位劃分資源,每一個隊列可設定必定比例的資源最低保證和使用上限。資源調度器老是優先知足最低資源保證,也就是說最低資源保證是每一個隊列分配資源的依據。
考慮下述極端狀況:集羣中部分隊列提交應用較多,負載較重,設定的最低保證資源不能知足全部Application的請求,致使大部分應用處於pending狀態;而與此同時,有部分隊列則負責較輕,使用的資源量低於最低資源保證,致使整個集羣資源利用率較低。
爲了提升資源使用率,合理分配集羣資源,YARN引入了資源搶佔功能,即資源調度器會將負載較輕的隊列的資源暫時分配給負載重的隊列(即最低資源保證並非硬資源保證,當隊列不須要太多資源時,並不會知足它的最低資源保證,而是暫時將空閒資源分配給其餘須要資源的隊列),僅當負載較輕隊列忽然收到新提交的應用程序時,調度器才進一步將本屬於該隊列的資源還給它。因爲此時資源可能正在被別的隊列使用,所以調度器必須等待其餘隊列釋放資源後,才能將這些資源「物歸原主」,這一般須要等待一段不肯定時間。爲了防止等待時間過長,調度器發現等待一段時間後若發現資源並未獲得釋放,則會強制進行資源回收。
CS特性:
Capacity調度器具備如下的幾個特性:
1. 層次化的隊列設計,這種層次化的隊列設計保證了子隊列可使用父隊列設置的所有資源。這樣經過層次化的管理,更容易合理分配和限制資源的使用。
2. 容量保證,隊列上都會設置一個資源的佔比,這樣能夠保證每一個隊列都不會佔用整個集羣的資源。
3. 安全,每一個隊列有嚴格的訪問控制。只能向本身的隊列裏面提交任務,並且不能修改或者訪問其餘隊列的任務。
4. 彈性分配,空閒的資源能夠被分配給任何隊列。當多個隊列出現爭用的時候,則會按照比例進行平衡。
5. 多租戶租用,經過隊列的容量限制,多個用戶就能夠共享同一個集羣,同事保證每一個隊列分配到本身的容量,提升利用率。
6. 操做性,yarn支持動態修改調整容量、權限等的分配,能夠在運行時直接修改。還提供給管理員界面,來顯示當前的隊列情況。管理員能夠在運行時,添加一個隊列;可是不能刪除一個隊列。管理員還能夠在運行時暫停某個隊列,這樣能夠保證當前的隊列在執行過程當中,集羣不會接收其餘的任務。若是一個隊列被設置成了stopped,那麼就不能向他或者子隊列上提交任務了。
7. 基於資源的調度,協調不一樣資源需求的應用程序,好比內存、CPU、資源(Hdfs數據分區)。
以上是對YARN調度的整理。OVER
熱文推薦
淺談微服務-兼容性
Spring Cloud Kubernetes之實戰一配置管理
Spring Cloud Kubernetes之實戰二服務註冊與發現
Spring Cloud Kubernetes之實戰三網關Gateway
若有收穫,點個在看,謝謝
本文分享自微信公衆號 - 程序猿Damon(Damon4X)。
若有侵權,請聯繫 support@oschina.cn 刪除。
本文參與「OSC源創計劃」,歡迎正在閱讀的你也加入,一塊兒分享。