Dinky 和 Flink CDC 在實時整庫同步的探索之路
摘要:本文整理自 Dinky 社區負責人,Apache Flink CDC contributor 亓文凱老師在 Flink Forward Asia 2024 數據集成(二)專場中的分享。主要講述 Dinky 的整庫同步技術方案演變至 Flink CDC Yaml 作業的探索歷程,并深入講解Flink CDC Yaml的一些細節能力。其主要分為三個部分:
1、起源
2、探索
3、未來
01.起源
1.1 數據集成的背景
本次分享圍繞數據集成,它也是 Flink CDC Yaml 作業的出現背景。在 Dinky 的眾多用戶中,我們總結出以下在傳統的數據集成方案中普遍會遇到的問題:需要將業務庫中的業務數據同步到分析庫中,起到解耦分析的作用,一般有三點要求。要求數據必須一致、鏈路要求穩定、數據時效性盡可能要高。
1.2 傳統數據集成方案
在傳統的數據集成方案中可以通過離線和實時兩條鏈路進行,離線通常會選擇開源的方案 DataX 或 Sqoop 來做一些快照同步,實時方案會根據數據庫類型進行選擇,例如 Mysql 數據庫采用 Debezium 或 Canal 實現增量同步,但是最終在分析庫中是兩種表的存在形式。需要在下一步數據加工治理過程中先將快照表和增量表合并為一張表,才能進行完整的一個統計分析。這樣會造成一個影響:全量和增量割裂,并且使用到的技術組件和鏈路較長,導致整體的數據時效性偏低。
1.3 Flink CDC 數據集成方案
Flink CDC 自發布以來,其中 2.0 版本帶來了重大更新,尤其是增量快照方法。可以將數據庫中的全量數據和增量實時數據合并,保證數據的一致性。其次采用 Flink CDC 時可以不需要部署 Debezium 或 Kafka 等其他組件,只需要 Flink CDC 一個組件就可以完成從業務庫到分析庫的實時一致性快照的同步。數據鏈路縮短,數據時效性比傳統的方案高。
1.4 數據集成面臨的挑戰——整庫同步
在去年經常會遇到一個場景:Flink CDC 在大面積使用的情況下,業務比較多,分析需求會逐步增長,所以構建了一個整庫同步的作業,將業務庫中的全部表或部分表同步到分析庫中。以往在技術瓶頸的限制下,開發方式是通過 Flink CDC 的 SQL 來完成對每一張表的處理。例如源庫中有一千張表,可能就需要開發一千個 Flink SQL 的作業,每一個作業會建立一個單獨的數據源連接,會消耗額外的連接數,Binlog 也會重復讀取。整個過程中會產生大量的 Flink 流作業,導致 Flink 集群越來越難以運維。這是遇到的第一個挑戰。
1.5 數據集成面臨的挑戰——模式演變
第二個挑戰是模式演變的問題。業務庫如果發生表結構變更,下游分析庫無法感知到。如果下游庫無法感知進行同步變更,此時數據鏈路仍然在進行同步,就會丟失一些新增的數據信息。例如增加了一個 age 列,如果下游庫沒有同步更新表結構就會丟失最新列的一些數據。
1.6 用戶渴望——端到端數據集成
用戶所渴望的是可以有全增量的自動切換、元數據可以自動發現、表結構可以自動同步、整庫同步只需要一個鏈接一個作業、在開發過程中只需一個 SQL 完成。
02.探索
2.1整庫同步的探索之路
先介紹一下 Dinky。Dinky 是一個以 Apache Flink 為內核構建的開源實時計算平臺,具備實時應用的作業開發、數據調試及運行監控能力,助力實時計算高效應用。
2.2 Dinky的介紹
Dinky 可以連接眾多的開源框架,例如 Paimon、Hudi、Iceberg 等其它數據庫和數據湖。Dinky 主要有兩個核心能力,第一是實時計算 IDE,可以對 Flink 作業、Flink SQL 和整庫同步作業進行調試,在 IDE 界面上實時展現任務的流數據,便于排查數據問題。第二是提供實時運維的能力,將 Flink 集群進行統一管理,可以對任務進行實時監控,觸發自定義的告警規則時,進行多渠道的告警通知。
2.3 Dinky基于Flink CDC的整庫同步探索
對于整庫同步,Dinky 還提供 CDC Source 的方案。此分享將對兩個方案進行對比。
Dinky 在實現 Flink CDC 整庫同步的探索上,通過實現一個 EXECUTE CDCSOURCE 的語法,讓用戶通過正則表達式等其他配置來完成整庫同步任務的定義,來實現全增量自動切換、元數據自動發現、結構變更自動同步、只用一個庫連接、一句 SQL 部署作業。此外,還支持寫入各種數據源、支持各種部署模式,這些額外能力在一定程度上緩解了 Flink CDC 在各種連接器 Source 和 Sink 上的不足。
2.4 Dinky CDC Source 整庫同步數據鏈路
Dinky CDC Source 整庫同步數據鏈路分析如下。在分庫分表的場景下,由 Source 節點將 Binlog 日志解析成 Debezium 格式的 Json,將 Json 數據按表名和主鍵進行分區,來支持下游多并行度的處理。下游按表名合并后進行分發,此處的表名合并主要用于分庫分表的場景,可以通過一些正則表達式和條件來指定分庫分表的規則。Route 可以將符合規則的表合并為一張表進行輸出。按表名合并后,會為下游每一張表產生對應算子。示例中有兩張表,就可以產生 Table1 和 Table2 兩條路線進行輸出。該 Pipeline 的實現主要基于 Process 和 Data Stream 來開發。為了適配更多的連接器,例如適配輸出到 Hudi 或 MySQL 數據庫,在最后一步 Data Sink 時也支持使用 Flink 的 SQL API 進行,這樣就可以兼容所有的 Flink SQL API,最終實現將 Flink CDC 支持的數據源整庫同步到任意一個 Flink SQL API 實現的數據庫。
由于基于 Data Stream 開發,所以模式演變比較受限,會導致模式演變受下游數據庫影響。例如 Doris Sink 支持下游演變,需要將數據流轉換為字符串的格式。所以我們可以進行一個鏈路的復用,將前面的 Debezium json 進行相關處理,到最后環節序列化成字符串,將字符串傳輸給 Doris Sink,由 Doris Sink 進行模式演變的處理。此時可能存在問題:當有多并行度任務時,例如多并行度為 2 時有兩個 Doris Sink 寫入同一張表,會存在模式演變時數據的丟失,一個算子在進行模式演變,另一個算子在進行數據寫入,這就是一個弊端。所以只能在并行度為 1 時正常使用。
2.5 Dinky CDC Source的局限性
Dinky CDC Source 存在一些局限性。
首先不支持自定義轉換,Dinky CDC Source 只支持寬容數據類型的轉換。
第二,由之前的算子拓撲圖可以發現,面對一些表同步時會構建大量的算子節點,這樣作業會非常龐大,從而會導致作業的恢復成本增加。
第三點是模式演變受限。本身框架不支持模式演變,需要由下游 Sink 連接器獨立實現。
2.6 Dinky CDC Source整庫同步的數據轉換探索
在 Dinky CDC Source 整庫同步的數據轉換探索上,由于下游可以支持 Table API 的使用,所以下游可以直接使用 Flink CTAS 語法,通過 Select 語句定義轉換,本質上使用 Flink SQL 的處理來進行。但是仍然會構建大量算子節點,且不支持模式演變。
2.7 Flink CDC YAML定義的Pipeline作業
去年 Flink CDC 3.0 發布,并貢獻給 Apache 孵化器。由于 Dinky CDC Source 存在嚴重的架構瓶頸,只能滿足一些特定情況下的整庫同步場景。經過調研后發現 Flink CDC YAML(Flink CDC Pipeline)作業完全重構了整庫同步的底層設計,支持模式演變和數據轉換的能力。
2.8 Flink CDC YAML核心架構
Flink CDC YAML 作業的架構主要核心是基于Flink 的運行環境來完成自定義算子的編排。在設計數據流時摒棄了 Flink SQL 的數據流,自定義了一些高效的數據結構。通過 Data Source、Data Sink、Schema Registry、Router 和 Transformer 五個算子來完成整個作業的編排。上游通過 Flink CDC Cli 和 Yaml 腳本來指定作業細節,完成整庫同步作業定義。
2.9 Flink CDC Pipeline 整庫同步鏈路
這是一張 Flink CDC Pipeline 的數據鏈路圖,模式演變、數據轉換和分庫分表三種場景結合使用。在經歷每個算子節點計算后,流數據的結構會發生變化。首先通過 Data Source 節點讀取到原始的 Schema 結構,使用數據轉換時引入 PreTransform 和 PostTransform 兩個算子。PreTransform 對無關的列進行刪除,裁剪后 Schema 更加簡潔。PostTransform 進行一些計算及投影等能力,包括兩部分,第一部分添加計算列,第二部分添加過濾條件,實現整庫同步鏈路中自定義數據轉換的能力。數據在投影后字段會增加,通常投影 Schema 會比之前的結構更寬。其中鏈路圖中的數據流長度可以反映出 Schema 大小的變化。下一步在 Schema operator 算子中對分庫分表場景下的一些結構進行進一步合并。不同的庫表可能會存在表結構不同、數據類型不同的問題。為了保證數據可以完整輸出到下游目標庫,通過對分庫分表場景的一些數據進行寬容處理,最終合并后的 Schema 大于等于投影后的 Schema 結構。此處在觸發模式演變時,通過對 DataChangeEvent 進行阻塞處理,保證下游數據庫數據正確一致性。解決了 Dinky CDC Source 在多并行度下進行模式演變的丟失部分變更數據的問題。
浙公網安備 33010602011771號