天天看點

Apache Hudi基礎知識整理

特性

Timeline

File Layout

Index

Table Types& Queries

Copy on Write Table

Merge on Read Table

本文整理自其他技術博文。

(1)快速upsert,可插入索引

(2)以原子方式操作資料并具有復原功能

(3)寫入器之和查詢之間的快照隔離

(4)savepoint使用者資料恢複的儲存點

(5)管理檔案大小,使用統計資料布局

(6)異步壓縮行列資料

(7)具有時間線來追蹤中繼資料血統

(8)通過聚類優化資料集

hudi的核心是維護在不同時刻在表上執行的所有操作的時間表,提供表的即時視圖,同時還有效地支援按時間順序檢索資料。Hudi的時刻由以下元件組成:

(1)<code>Instant action</code>: 在表上執行的操作類型

(2)<code>Instant time</code>: 即時時間,通常是一個時間戳,它安裝action的開始時間單調遞增

(3)<code>State</code>: 時刻的目前狀态

hudi保證在時間線上的操作都是基于即時時間的,兩者的時間保持一緻并且是原子性的。

<code>acion</code>操作包括:

(1)<code>commits</code>: 表示将一批資料原子寫入表中

(2)<code>cleans</code>: 清除表中不再需要的舊版本檔案的背景活動。

(3)<code>delta_commit</code>:增量送出,是指将一批資料原子性寫入<code>MergeOnRead</code>類型的表中,其中部分或者所有資料可以寫入增量日志中。

(4)<code>compaction</code>: 協調hudi中差異資料結構的背景活動,例如:将更新從基于行的日志檔案變成列格式。在内部,壓縮的表現為時間軸上的特殊送出。

(5)<code>rollback</code>:表示送出操作不成功且已經復原,會删除在寫入過程中産生的資料

(6)<code>savepoint</code>:将某些檔案标記為“已儲存”,以便清理程式時不會被清除。在需要資料恢複的情況下,有助于将資料集還原到時間軸上某個點。

<code>state</code>類型:

(1)<code>requested</code>:表示一個動作已被安排,但尚未啟動

(2)<code>inflight</code>:表示目前正在執行操作

(3)<code>completed</code>:表示在時間線上完成了操作

Apache Hudi基礎知識整理

上圖顯示了hudi表上10:00和10:20之間發生的更新插入,每5分鐘一次,将送出中繼資料以及其他背景清理/壓縮操作在hudi時間軸上。觀察的關鍵點是,送出時間表示資料的到達時間,而實際資料組織則反應了實際時間或事件時間,即資料所反映的從07:00開始的每小時時段。在權衡資料延遲和完整性,這是兩個關鍵概念。

如果有延遲到達的資料(事件時間為9:00的資料在10:20達到,延遲&gt;1小時),可以看到upsert将資料生成到更舊的時間段/檔案夾中。在時間軸的幫助下,增量查詢可以隻提取10:00以後成功送出的新資料,并非高效地隻消費更改過的檔案,且無需掃描更大的檔案範圍,例如07:00後的所有時間段。

Hudi會在DFS分布式檔案系統上的basepath基本路徑下組織成目錄結構。每張對應的表都會成多個分區,這些分區是包含該分區的資料檔案的檔案夾,與hive的目錄結構非常相似。

在每個分區内,檔案被組織成檔案組,檔案id為唯一辨別。每個檔案組包含多個切片,其中每個切片包含在某個送出/壓縮即時時間生成的基本列檔案(parquet檔案),以及自生成基本檔案以來對基本檔案的插入/更新的一組日志檔案(*.log)。Hudi采用<code>MVCC</code>設計,其中壓縮操作會将日志和基本檔案合并成新的檔案片,清理操作會将未使用/較舊的檔案片删除來回收DFS上的空間。

Hudi通過索引機制将映射的給定的<code>hoodie key</code>(record key+partition path)映射到檔案id(唯一辨別),進而提供高效的upsert操作。記錄鍵和檔案組/檔案ID之間的這種映射,一旦記錄的第一個版本寫入檔案就永遠不會改變。

Hudi表類型定義了如何在DFS上對資料進行索引和布局,以及如何在此類組織上實作上述操作和時間軸活動(即如何寫入資料)。同樣,查詢類型定義了底層資料如何暴露給查詢(即如何讀取資料)。

Table Type

Supported Query types

Copy on Write (寫時複制)

快照查詢+增量查詢

Merge on Read (讀時合并)

快照查詢+增量查詢+讀取優化查詢(近實時)

Table Types:

Copy on Write:使用列式存儲來存儲資料(例如:parquet),通過在寫入期間執行同步合并來簡單地更新和重制檔案

Merge on Read:使用列式存儲(parquet)+行式檔案(arvo)組合存儲資料。更新記錄到增量檔案中,然後進行同步或異步壓縮來生成新版本的列式檔案。

下面總結了兩種表類型之間的權衡

權衡

CopyOnWrite

MergeOnRead

資料延遲

查詢延遲

Update(I/O) 更新成本

高(重寫整個Parquet檔案)

低(追加到增量日志)

Parquet File Size

低(更新成本I/O高)

較大(低更新成本)

Write Amplification(WA寫入放大)

低(取決于壓縮政策)

Query Types:

(1)<code>Snapshot Queries</code>:快照查詢,在此視圖上的查詢将看到某個送出和壓縮操作的最新快照。對于<code>merge on read</code>的表,它通過即時合并最新檔案切片的基本檔案和增量檔案來展示近乎實時的資料(幾分鐘)。對于<code>copy on write</code>的表,它提供了對現有<code>parquet</code>表的直接替代,同時提供了<code>upsert/delete</code>和其他寫入功能。

(2)<code>Incremental Queries</code>:增量查詢,該視圖隻能看到從某個送出/壓縮寫入資料集的新資料。該視圖有效地提供了change stream,來支援增量視圖

(3)<code>Read Optimized Queries</code>:讀優化視圖,在此視圖上的查詢将檢視到給定送出或壓縮操作中的最新快照。該視圖将最新檔案切片的列暴露個查詢,并保證與非hudi列式資料集相比,具有相同列式查詢功能。

下面總結了兩種查詢的權衡

Snapshot

Read Optimized

高(合并列式基礎檔案+行式增量日志檔案)

低(原始列式資料)

<code>Copy on Write</code>表中的檔案切片僅包含基本/列檔案,并且每次送出都會生成新版本的基本檔案。換句話說,每次送出操作都會被壓縮,以便存儲列式資料,是以Write Amplification寫入放大非常高(即使隻有一個位元組的資料被送出修改,我們也需要重寫整個列資料檔案),而讀取資料成本則沒有增加,是以這種表适合于做分析工作,讀取密集型的操作。

下圖說明了copy on write的表是如何工作的:

Apache Hudi基礎知識整理

随着資料被寫入,對現有檔案組的更新會為該檔案組生成一個帶有送出即時時間标記的新切片,而插入配置設定一個新檔案組并寫入該檔案組第一個切片。這些切片和送出即時時間在上圖用同一顔色辨別。針對圖上右側sql查詢,首先檢查時間軸上的最新送出并過濾掉之前的舊資料(根據時間查詢最新資料),如上圖所示粉色資料在10:10被送出,第一次查詢是在10:10之前,是以出現不到粉色資料,第二次查詢時間在10:10之後,可以查詢到粉色資料(已被送出的資料)。

Copy on Write表從根本上改進表的管理方式

(1)在原有檔案上進行自動更新資料,而不是重新重新整理整個表/分區

(2)能夠隻讀取修改部分的資料,而不是浪費查詢無效資料

(3)嚴格控制檔案大小來保證查詢性能(小檔案會顯著降低查詢性能)

<code>Merge on Read</code>表是<code>copy on write</code>的超集,它仍然支援通過僅向使用者公開最新的檔案切片中的基本/列來對表進行查詢優化。使用者每次對表檔案的upsert操作都會以增量日志的形式進行存儲,增量日志會對應每個檔案最新的ID來幫助使用者完成快照查詢。是以這種表類型,能夠智能平衡讀取和寫放大(wa),提供近乎實時的資料。這種表最重要的是壓縮器,它用來選擇将對應增量日志資料壓縮到表的基本檔案中,來保持查詢時的性能(較大的增量日志檔案會影響合并時間和查詢時間)

下圖說明了該表的工作原理,并顯示兩種查詢類型:快照查詢和讀取優化查詢

Apache Hudi基礎知識整理

(1)如上圖所示,現在每一分鐘送出一次,這種操作是在<code>copy on write</code> 表裡無法做到的。

(2)現在有一個增量日志檔案,它儲存對基本列檔案中記錄的傳入更新(對表的修改),在圖中,增量日志檔案包含從<code>10:05</code>到<code>10:10</code>的所有資料。基本列檔案仍然使用commit來進行版本控制,是以如果隻看基本列檔案,那麼表的表的布局就像copy on write表一樣。

(3)定期壓縮過程會協調增量日志檔案和基本列檔案進行合并,并生成新版本的基本列檔案,就如圖中10:05所發生的情況一樣。

(4)查詢表的方式有兩種,Read Optimized query和Snapshot query,取決于我們選擇是要查詢性能還是資料新鮮度

(5)如上圖所示,Read Optimized query查詢不到10:05之後的資料(查詢不到增量日志裡的資料),而Snapshot query則可以查詢到全量資料(基本列資料+行式的增量日志資料)。

(6)壓縮觸發是解決所有難題的關鍵,通過實施壓縮政策,會快速縮新分區資料,來保證使用者使用Read Optimized query可以查詢到X分鐘内的資料

Merge on Read Table是直接在DFS上啟用近實時(near real-time)處理,而不是将資料複制到外部專用系統中。該表還有些次要的好處,例如通過避免資料的同步合并來減少寫入放大(WA)