深入解讀Flink資源管理機制

作者:宋辛童(五藏)
整理:王文傑(Flink 社區志願者)

摘要:本文根據 Apache Flink 系列直播整理而成,由阿里巴巴高級開發工程師宋辛童分享。文章主要從基本概念、當前機制與策略、未來發展方向等三個方面幫助開發者深入理解 Flink 的資源管理機制。

  1. 基本概念
  2. 當前機制與策略
  3. 未來發展方向

Tips:點擊「下方鏈接」可查看更多數倉系列視頻~
https://ververica.cn/developers/flink-training-course-data-warehouse/

1. 基本概念

1.1 相關組件

我們今天介紹的主要是與 Flink 資源管理相關的組件,我們知道一個 Flink Cluster 是由一個 Flink Master 和多個 Task Manager 組成的,Flink Master 和 Task Manager 是進程級組件,其他的組件都是進程內的組件。

圖1. Flink 資源管理相關組件.png
圖1. Flink 資源管理相關組件

如圖1所示,一個 Flink Master 中有一個 Resource Manager 和多個 Job Manager ,Flink Master 中每一個 Job Manager 單獨管理一個具體的 Job ,Job Manager 中的 Scheduler 組件負責調度執行該 Job 的 DAG 中所有 Task ,發出資源請求,即整個資源調度的起點;JobManager 中的 Slot Pool 組件持有分配到該 Job 的所有資源。另外,Flink Master 中唯一的 Resource Manager 負責整個 Flink Cluster 的資源調度以及與外部調度系統對接,這裏的外部調度系統指的是 Kubernetes、Mesos、Yarn 等資源管理系統。

Task Manager 負責 Task 的執行,其中的 Slot 是 Task Manager 資源的一個子集,也是 Flink 資源管理的基本單位,Slot 的概念貫穿資源調度過程的始終。

1.2 邏輯層級

介紹完相關組件,我們需要了解一下這些組件之間的邏輯關係,共分如下爲4層。

  • Operator
  • 算子是最基本的數據處理單元
  • Task
  • Flink Runtime 中真正去進行調度的最小單位
  • 由一系列算子鏈式組合而成(chained operators)

(Note:如果兩個 Operator 屬於同一個 Task,那麼不會出現一個 Operator 已經開始運行另一個 Operator 還沒被調度的情況。)

  • Job
  • 對應一個 Job Graph
  • Flink Cluster
  • 1 Flink Master + N Task Managers

圖2. 組件的邏輯層級.png
圖2. 組件的邏輯層級

資源調度的範疇,實際上是圖2紅框內的內容。剛剛介紹的與資源調度相關的組件中,JobManager、Secheduler 和 Slot Pool 對應於 Job 級別,Resource Manager、Slot Manager 和 Task Manager 對應於 Flink Cluster 級別。

在 Operator 和 Task 中間的 Chaining 是指如何用 Operator 組成 Task 。在 Task 和 Job 之間的 Slot Sharing 是指多個 Task 如何共享一個 Slot 資源,這種情況不會發生在跨作業的情況中。在 Flink Cluster 和 Job 之間的 Slot Allocation 是指 Flink Cluster 中的 Slot 是怎樣分配給不同的 Job 。

1.3 兩層資源調度模型

Flink 的資源調度是一個經典的兩層模型,其中從 Cluster 到 Job 的分配過程是由 Slot Manager 來完成,Job 內部分配給 Task 資源的過程則是由 Scheduler 來完成。如圖3,Scheduler 向 Slot Pool 發出 Slot Request(資源請求),Slot Pool 如果不能滿足該資源需求則會進一步請求 Resource Manager,具體來滿足該請求的組件是 Slot Manager。

圖3. 兩層資源調度模型.png
圖3. 兩層資源調度模型

Task 對 Slot 進行復用有兩種方式:

  • Slot Caching
  • 批作業
  • 流作業的 Failover
  • 多個 task 先後/輪流使用 slot 資源
  • Slot Sharing
  • 多個 Task 在滿足一定條件下可同時共享同一個 Slot 資源

2. 當前機制與策略

截至 Flink 1.10 版本,Flink 當前的資源管理機制與策略是怎樣的?以下將詳細說明。

2.1 Task Manager 有哪些資源?

圖4. Task Manager 資源組成.png
圖4. Task Manager 資源組成

  • 資源類型
  • 內存
  • CPU
  • 其他擴展資源
  • GPU(FLIP-108,在 Flink 1.11 版本完成)
  • TM 資源由配置決定
  • Standalone 部署模式下,TM 資源可能不同
  • 其他部署模式下,所有 TM 資源均相同

2.2 Slot 有哪些資源?

圖5. Slot資源組成.png
圖5. Slot資源組成

Task Manager 中有固定數量的 Slot ,Slot 的具體數量由配置決定。同一 Task Manager 上 Slot 之間沒有差別,每一個 Slot 都一樣大,即資源一樣多。

2.3 Flink Cluster 有多少 Task Manager ?

  • Standalone 部署模式

在 Standalone 部署模式下,Task Manager 的數量是固定的,如果是 start-cluster.sh 腳本來啓動集羣,可以通過修改以下文件中的配置來決定 TM 的數量;也可以通過手動執行 taskmanager.sh 腳本來啓動一個 TM 。

<FLINK_DIR>/conf/slaves
  • Active Resource Manager 部署模式
  • Kubernetes,Yarn,Mesos
  • 由 SlotManager / ResourceManager 按需動態決定
  • 當前 Slot 數量不能滿足新的 Slot Request 時,申請並啓動新的 TaskManager
  • TaskManager 空閒一段時間後,超時則釋放

Note:On-Yarn 部署模式不再支持指定固定數量的 TM ,即以下命令參數已經失效。

yarn-session.sh -n <num>
flink run -yn <num>

2.4 Cluster -> Job 資源調度的過程

圖6. Cluster 到 Job 的資源調度過程.png
圖6. Cluster 到 Job 的資源調度過程

如圖6,Cluster 到 Job 的資源調度過程中主要包含兩個過程。

  • Slot Allocation(圖6中紅色箭頭)

Scheduler 向 Slot Pool 發送請求,如果 Slot 資源足夠則直接分配,如果 Slot 資源不夠,則由 Slot Pool 再向 Slot Manager發送請求(此時即爲 Job 向 Cluster 請求資源),如果 Slot Manager 判斷集羣當中有足夠的資源可以滿足需求,那麼就會向 Task Manager 發送 Assign 指令,Task Manager 就會提供 Slot 給 Slot Pool,Slot Pool 再去滿足 Scheduler 的資源請求。

  • Starting TaskManagers(圖6中藍色箭頭)

在 Active Resource Manager 資源部署模式下,當 Resource Manager 判定 Flink Cluster 中沒有足夠的資源去滿足需求時,它會進一步去底層的資源調度系統請求資源,由調度系統把新的 Task Manager 啓動起來,並且 TaskManager 向 Resource Manager 註冊,則完成了新 Slot 的補充。

2.5 Job -> Task 資源調度的過程

  • Scheduler
  • 根據 Execution Graph 和 Task 的執行狀態,決定接下來要調度的 Task
  • 發起 SlotRequest
  • 決定 Task / Slot 之間的分配
  • Slot Sharing
  • Slot Sharing Group 中的任務可共用Slot
  • 默認所有節點在一個 Slot Sharing Group 中
  • 一個 Slot 中相同任務只能有一個
  • 優點
  • 運行一個作業所需的 Slot 數量爲最大併發數
  • 相對負載均衡

圖7. Job 到 Task 資源調度過程.png
圖7. Job 到 Task 資源調度過程

Slot Sharing 過程如圖7所示(每一行分別是一個 task 的多個併發,自下而上分別是 A、B、C),A、B、C 的並行度分別是4、4、3,這些 Task 屬於同一個 Slot Sharing Group 中,所以不同的 Task 可以放在相同的 Slot 中運行,如圖7右側所示,有3個 Slot 放入了 ABC,而第四個 Slot 放入了 AB 。通過以上過程我們可以很容易推算出這個 Job 需要的 Slot 數是4,也是最大併發數。

2.6 資源調優

通過以上介紹的機制,我們容易發現,Flink 所採用的是自頂向下的資源管理,我們所配置的是 Job 整體的資源,而 Flink 通過 Slot Sharing 機制控制 Slot 的數量和負載均衡,通過調整 Task Manager / Slot 的資源,以適應一個 Slot Sharing Group 的資源需求。Flink 的資源管理配置簡單,易用性強,適合拓撲結構簡單或規模較小的作業。

3. 未來發展方向

3.1 細粒度資源管理

■ Slot Sharing 的侷限性

圖8. Slot Sharing的侷限性.png
圖8. Slot Sharing的侷限性

  • 資源利用率非最優

通過 Slot Sharing 機制我們可以看到,對資源的利用率不是最優的,因爲我們是按照最大併發數來配置 Slot 的資源,這樣就會造成如圖8所示的部分資源被浪費。

圖9. Slot Sharing 的不確定性.png

  • 不確定性

如圖9所示,A 的併發度是2,BC 的併發度是1,圖9中的兩種分配方式均滿足 Slot Sharing 機制的要求,這樣就可能會出現如下情況:我們在測試的時候出現的是上圖右邊這種 Slot 資源配置情況,我們進行了調優配置好了 Slot 的大小,但是我們真正提交作業到生產環境中確是上圖左邊的情況,這樣就會造成資源不夠用,進而導致作業無法執行。

■ 細粒度資源管理

基於以上 Slot Sharing 機制的侷限性,我們提出了細粒度資源管理的概念。

  • 當算子的資源需求是已知的,可以通過經驗性的預估、半自動化或自動化的工具來衡量 Slot 的資源大小。
  • 每一個 Task 獨佔一個 Slot 來進行資源調度。

3.2 動態 Slot 切分

圖10. 靜態 Slot 分配.png
圖10. 靜態 Slot 分配

如圖10所示,我們用圓圈的大小來表示該任務所需資源的多少,如果不採用 Slot Sharing Group 機制,現有的 Flink 資源管理機制要求 Slot 的大小必須一致,所以我們可以得到右側這樣的 Slot 資源配置,四個 Task Manager。

圖11. 動態 Slot 切分.png
圖11. 動態 Slot 切分

如果我們可以根據不同任務動態的決定每個 Slot 的大小,我們就可以將 Task Manager 切分成如圖11所示的情況,僅需要三個 Task Manager。

  • 動態 Slot 切分(FLIP-56)

圖12. 靜態 Slot 劃分.png
圖12. 靜態 Slot 劃分

如圖12所示,這是當前靜態的固定大小的 Task Manager 的管理方式,隨着任務的執行,Slot 只能簡單的被佔用或者被釋放,而不能進行更多額外調整。

圖13. 動態 Slot 劃分.png
圖13. 動態 Slot 劃分

如圖13所示,每一個 Task Manager 啓動之後是一整塊的資源,每接收一個資源請求時,都可以根據該請求動態的切分出一個 Slot 提供給它。但這也是有缺陷的,因爲不管我們怎樣切分,都經常會出現一小部分資源被浪費的情況,這也是我們常說的資源碎片問題。

3.3 碎片化問題

針對上述提到的資源碎片問題,我們提出了一個解決方案,可以根據 Slot Request 資源需求定製 Task Manager 資源,當前Flink 1.10 中每一個 Task Manager 都是一致的,但是在細粒度的資源管理中,已知資源需求時,完全可以定製 Task Manager,從理論上講是完全可以徹底杜絕資源碎片問題。

這樣做的代價是需要延長作業的調度時間,要想定製 Task Manager 就必須要等收到 Slot Request 後纔可以,啓動 Task Manager 的過程是比較耗時的。另一方面,可能會導致 Task Manager 比較難複用,很有可能需要釋放掉舊的 Task Manager 而啓動新的,這也會耗費很多時間。

在不同的應用場景下也可使用不同的方案:

  • Streaming(流處理)
  • 一次調度,長期運行
  • 提高資源利用率的收益較高
  • 適合採用定製 Task Manager 資源的調度策略
  • Batch(批處理,尤其是短查詢)
  • 頻繁調度,Task 運行時間短
  • 對調度延遲敏感
  • 適合採用非定製的 Task Manager 資源的調度策略

3.4 易用性問題

與現有的資源調優相反,細粒度資源管理下的資源調優是自底向上的資源管理,我們不再是需要配置 Job 的整體資源,而是需要用戶去配置每個 Task 具體的資源需求,我們需要把 Task 的資源配置儘可能的接近其實際的資源需求,來提高資源利用率。但是同樣帶來的問題是,配置難度高。所以更適用於拓撲復雜或規模較大的作業。

與當前的資源調優相比,兩種機制並不是孰優孰劣的關係,而是可以針對不同的場景需求適配不同的調優策略,在社區看來,兩種策略均有存在的價值。

3.5 資源調度策略插件化(FLINK-14106)

不管是當前靜態的資源管理機制,還是細粒度資源管理機制都要求調度策略針對不同的場景來進行不同的變化。目前 Flink 1.11 中調度策略插件化的開發工作已經完成。

  • 資源調度策略
  • Task Manager 的數量
  • 何時申請/釋放 Task Manager
  • Task Manager 的資源大小
  • Slot Request 與 Task Manager 資源之間的適配

通過這三個資源調度策略,我們可以得到如下優勢:

  • 解決流處理和批處理的不同資源調度策略需求
  • 滿足用戶對於細粒度、非細粒度資源管理的不同選擇
  • 未來更多資源調度策略帶來的可能性
  • 例如:Spark 根據負載彈性伸縮集羣的策略

隨着 Flink 支持越來越多的應用場景,靈活的資源調度策略對於保障高性能及資源效率至關重要,我們歡迎更多 Flink 愛好者和開發者加入我們社區,攜手共進。

作者介紹:

宋辛童(五藏),阿里巴巴高級開發工程師。2018 年博士畢業於北京大學網絡與信息系統研究所,後加入阿里巴巴實時計算團隊,主要負責 Apache Flink 及阿里巴巴企業版本 Blink 中資源調度與管理機制的研發工作。

原文鏈接
本文爲雲棲社區原創內容,未經允許不得轉載。

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