Flink 在米哈遊的落地實踐

ApacheFlink發表於2022-03-30

摘要:本文是來自米哈遊大資料部實時計算負責人張劍對於 Flink 在米哈遊應用及實踐的分享。本篇內容主要分為四個部分:

  1. 背景介紹
  2. 實時平臺建設
  3. 實時數倉和資料湖探索
  4. 未來發展與展望

一、背景介紹

米哈遊成立於 2011 年,致力於為使用者提供美好的、超出預期的產品與內容。公司陸續推出了多款高品質人氣產品,包括《崩壞學園2》、《崩壞3》、《未定事件簿》、《原神》,動態桌面軟體《人工桌面》以及社群產品《米遊社》,並圍繞原創 IP 打造了動畫、漫畫、音樂、小說及周邊等多元產品。總部位於中國上海,並在新加坡、美國、加拿大、日本、韓國等國家和地區進行全球化佈局。

Flink 在米哈遊大資料發展過程中,一直扮演著重要角色。自實時計算平臺建立以來,Flink 作為實時計算引擎,經歷了多個發展階段,實時計算平臺也在不斷地迭代完善。在米哈遊內部,實時計算平臺被稱作 Mlink,主要以 Flink 為主,相容 Spark Streaming 任務。從起初的 Flink Jar 包任務為主,發展到以 Flink Sql 為主,不斷的降低了使用門檻和提高了任務的開發效率;從起初基礎的 Flink 任務開發,發展到跨區域、跨雲廠商的任務多版本管理,滿足了業務發展的需求。在發展的過程中,米哈遊不斷地關注著社群的發展,並同社群和阿里雲同學保持密切的聯絡。

Mlink 主要是基於 Yarn 資源管理的計算平臺,支援了數倉、演算法、推薦、風控、大屏等業務。任務數 1000+,Sql 任務佔比 80% 左右。使用的 Yarn Vcores 超 5000 核,記憶體 10T 左右,其中單個任務峰值吞吐在 500 萬 QPS,每天吞吐的資料規模超千億。

二、實時平臺建設

2.1 遇到的問題

在 Flink 探索發展的過程中,都會遇到 Flink 使用的一些痛點,大家遇到的,同樣在我們探索和實踐的過程中也有所感觸。總結起來,大概是以下五個方面:

  • 一是 Jar 任務的開發成本高,對於不熟悉 Flink 程式碼的同學來說使用成本過高。同時,Jar 任務維護成本高,一些程式碼邏輯的改動會涉及到重新打包、上傳,上線等動作;
  • 二是任務管理功能缺失,其中多租戶、歷史版本回溯、開發版本和線上版本管理、UDF 管理、血緣管理是實時平臺管理的重要內容;
  • 三是 Flink 引擎本身管理,主要涉及到多 Flink 版本管理,任務引數配置、常用 Connector 的二次開發、多資源環境管理等問題;
  • 四是任務的告警監控管理,任務問題診斷;
  • 五是同離線數倉互通,包括 Hive Catalog 管理,實時和離線排程依賴管理等。

上面的五個問題,可能是普遍的問題,所以各家公司都會基於內部自建或者開源專案二次開發,來滿足自身任務開發管理需求。對於米哈遊,除了上述五個問題,還存在跨區域、跨雲廠商中遇到的問題需要解決,主要是跨區域之後,任務上線和提交效率,跨雲廠商,資源環境不一致等。

2.2 解決方案

實時平臺建設主要圍繞如上問題。目前實時平臺架構如下:

img

圖 1:多雲多環境實時平臺架構

前端控制雲環境的切換。Backend Service 主要負責使用者許可權管理、任務的多版本管理、血緣管理,任務運維,任務上下線,任務監控和告警等工作。Executor Service 主要負責任務解析、任務提交執行、任務下線和同各類資源管理器互動等工作。其中,Backend Service 到 Executor Service 通過 Thrift 協議通訊,Executor Service 的實現可以多語言擴充套件。架構設計主要解決跨地區跨雲廠商問題,實現任務管理和任務執行之間解耦。

img

圖 2:Mlink 平臺開發頁面

img

圖 3:Mlink平臺運維頁面

img

圖 4:Mlink 平臺同步任務頁面

Mlink 實時計算平臺主要設計了概覽、開發、資源管理、運維、資料探查、同步任務、使用者管理和執行器管理等模組。其中開發頁面主要是使用者編寫任務和引數配置,包含歷史版本管理等內容。資源管理主要是 Jar 包任務和 UDF 管理。運維主要是任務啟停、任務執行監控、任務告警配置等。資料探查部分主要是預覽部分資料功能,比如 Kafka Topic 支援按分割槽、按時間或者 Offset 預覽資料。同步任務主要是為了方便管理同步任務,比如 CDC 到 Iceberg 一鍵同步和執行管理。執行器負責 Executor 的運維工作,包括 Executor 上下線,健康狀態監控等。

2.3 遇到的挑戰

平臺建設和迭代過程中,我們遇到了不少的挑戰,也產生了一些比較好的實踐。主要分享四個方面。

第一是 Executor Service 開發和維護方面。

Executor 主要涉及到 Jar 和 Sql 任務解析提交部分。一開始的方案為了解決跨地區傳輸效率問題,特別是大的 jar 包傳輸,由後端進行任務解析,最後傳輸 job graph 到 Executor,Executor 再通過資源管理器 Api 提交,這個因為後端解析環境不一致問題,部分任務解析過程中會存在 action 動作,特別是涉及到 Hive 表和 Iceberg 表部分。最後採用後端不執行,改由 Executor 解析的方案。Executor 在解析過程中,遇到了 Executor 在執行很長一段時間後,會出現元空間 OOM 的情況。這個主要是因為 Executor 不斷的載入任務需要 Class 類,會導致使用的元空間記憶體不斷增加。這個主要是通過任務解析完成之後,解除安裝類載入器和堆 GC 設定來解決。

第二是監控方面。

監控採用的是 Influxdb 加 Grafana 的方案。隨著任務量的不斷增加,Influxdb 儲存的 Series 超過百萬,影響監控檢視的穩定性,查詢響應緩慢。一是擴充套件 Influxdb,執行端通過一致性 hash 的方案,分配任務 Metric 上報到不同 Influxdb。本身通過對 Flink 任務上報 Metric 進行一定程度的精簡。其次在監控上,比如 Kafka 消費監控,目前是支援消費條數的延遲監控,自定義了 Kafka 消費延遲時間的監控,主要是採集了 Kafka 最慢並行度消費的時間,能夠反映 Kafka 消費的最大延遲時間,能夠反映某個時間點的資料一定被消費了。

img

圖 5:Grafana 監控示例

第三是 Connector 二次開發方面。

在 CDC 1.0 版本基礎上迭代,支援 Mysql 採集的時候動態擴充套件欄位和基於時間啟動消費位點、採集的庫表、位點等 Schema 資訊。在 CDC 2.0 版本基礎上,增加了全量讀取庫表流控和不需要 MySQL 開啟 Binlog 的全量初始化功能。其中多 CDC 例項同步可能會對上游 Mysql 造成壓力,採用了 Kafka 作為資料中轉,根據庫表主鍵欄位作為 Topic 的 Key,保證 Binlog 的順序,在下游不會出現資料亂序。

Iceberg 作為資料湖方案,改造的點主要是 Iceberg V2 表的支援上面,也就是 Upsert 表。建立 Iceberg 管理中心,會根據合併策略定期優化和清理,Flink 寫入主要保證在 CDC 到 Iceberg V2 表順序性,在如何減少 Delete File 上,在 Iceberg 寫入上增加了 BloomFilter 的支援,能夠顯著減少 Delete File 大小。Iceberg 管理中心,支援了 V2 表合併和 Flink 提交衝突問題。

Clickhouse 方面,重構了 Clickhouse 寫入程式碼,優化了 Clickhouse 的寫入效能,支援了本地表和分散式表寫入。

第四是資料入湖和離線排程方面。

實時平臺整合了 Iceberg,並支援 Iceberg Hadoop、Hive、Oss、S3 多種 Catalog。CDC 到 Iceberg 入湖鏈路已經在部門生產業務上線使用。在資料入湖或者入倉中,如果下游表有被離線數倉用到的地方,都會有依賴排程問題,離線任務何時啟動?目前我們主要通過計算任務的延遲時間和 Checkpoint 時間來確保資料已經入倉入湖。以 CDC 或者 Kafka 到 Iceberg 為例。首先採集 CDC 端採集延遲時間,Kafka 採集最慢並行度延遲時間,同時採集任務 Checkpoint 時間。現在的 Checkpoint 完成,Iceberg 版本不一定會更新,基於此,對 Iceberg 寫入進行了改造。這樣一個同步任務,如果 CDC 採集端沒有延遲,Checkpoint 也已經完成,可以保證某個小時的資料一定已經入倉。實時平臺提供任務延遲查詢介面。離線排程以此介面為排程依賴節點。這樣就保證了離線任務啟動時候,入倉資料的完整性。

三、實時數倉和資料湖探索

實時資料採集,目前主要是三條鏈路:

  • 一是日誌型別,主要是通過 Filebeat 採集寫入 Kafka,Es 作為 Filebeat 的監控;
  • 二是 Api 介面上報服務,後端接入 Kafka;
  • 三是 CDC 採集全量加增量 Mysql 資料,寫入 Kafka 或者直接寫入 Iceberg。之前是採用 Canal 作為增量採集方案,現在已經全部改為了 CDC。

實時數倉架構設計和業內基本一致,包括 ODS、DWD、DWS 層,之後輸出到各應用系統,比如 Clickhouse、Doris、Mysql、Redis 等。目前主要以 Kafka 作為中間承載,也在探索 Iceberg 作為中間層的使用。Iceberg 雖然具有流讀功能,但是流讀時候資料的順序性問題,一直沒有較好的方案解決,我們也是在探索過程中。探索的主要方向有兩個:

  • 一是將 Kafka 和 Iceberg 作為混合 Source 方案,Flink 任務讀取混合 Source 之後,基於 Iceberg 快照記錄的 Kafka 位點,確定讀取範圍和切換點;
  • 二是社群 Flip-188 提出的引入 Dynamic Table 儲存實現。Flink 內建表由兩部分組成,LogStore 和 FileStore。LogStore 將滿足訊息系統的需要,而 FileStore 是列式格式檔案系統。在每個時間點,LogStore 和 FileStore 都會為最新寫入的資料儲存完全相同的資料 (LogStore 有 TTL),但物理佈局不同。

在實時數倉探索方面,主要是 CDC 到 Iceberg 入湖任務,已經在生產上使用。其中主要解決了四個問題:

  • 一是 CDC 採集問題,特別是多庫多表採集,會集中採集到 Kafka,減少多個 CDC 任務對同一資料庫影響;
  • 二是 Iceberg 支援 V2 表寫入,包括寫入的索引過濾減少 Delete 檔案,Iceberg 管理中心合併和提交衝突;
  • 三是支援分庫分表的資料校驗和資料延遲檢查;
  • 四是一鍵式任務生成。對於使用者而言,只需要填寫資料庫相關資訊,目標 Iceberg 表庫名和表名,並支援使用 Kafka 中轉,避免多個 CDC 例項採集同一個資料庫例項。

通過上述四個問題的解決,能夠達到資料庫資料分鐘級資料入湖,入湖的資料校驗和資料延遲依賴達成,方便下游離線任務排程啟動。

img

圖 6:資料入湖鏈路

四、未來發展與展望

主要有四點:

  • 一是 Flink 動態表儲存能夠儘快實現落地,實現真正的實時數倉和流表一體;
  • 二是 Flink 任務動態擴縮容、基於任務診斷的主動資源調整、細粒度資源調整;
  • 三是 Flink 對批任務的讀寫優化,目前批任務 Flink 的使用面不如 Spark,如果未來能夠在此補足,可以做到流批操作一個引擎,開發成本會顯著降低;
  • 四是 Flink 加資料湖更好的落地推廣。

點選檢視更多技術內容

更多 Flink 相關技術問題,可掃碼加入社群釘釘交流群
第一時間獲取最新技術文章和社群動態,請關注公眾號~

image.png

相關文章