總述
hudi提供了hudi表的概念,這些表支援CRUD操作,可以利用現有的大資料叢集比如HDFS做資料檔案存儲,然後使用SparkSQL或Hive等分析引擎進行資料分析查詢
![](https://img.laitimes.com/img/_0nNw4CM6IyYiwiM6ICdiwiI0gTMx81dsQWZ4lmZf1GLlpXazVmcvwFciV2dsQXYtJ3bm9CX9s2RkBnVHFmb1clWvB3MaVnRtp1XlBXe0xCMy81dvRWYoNHLwEzX5xCMx8FesU2cfdGLwMzX0xiRGZkRGZ0Xy9GbvNGLpZTY1EmMZVDUSFTU4VFRR9Fd4VGdsYTMfVmepNHLrJXYtJXZ0F2dvwVZnFWbp1zczV2YvJHctM3cv1Ce-cmbw5SO5UDO5EjY0ATM0QmZlJTYyYzX2MjNxUTMwEzLcZDMyIDMy8CXn9Gbi9CXzV2Zh1WavwVbvNmLvR3YxUjLyM3Lc9CX6MHc0RHaiojIsJye.png)
hudi表的三個主要元件
a.有序的時間軸中繼資料,類似于資料庫事務日志
b.分層布局的資料檔案:實際寫入表中的資料
c.索引(多種實作方式):映射包含指定記錄的資料集;資料有唯一主鍵,可快速定位資料
1.時間軸Timeline[核心]
在所有的表中維護了一個包含在不同的即時(Instant)時間對資料集操作(比如新增、修改或删除)的時間軸(Timeline)
在每一次對hudi表的資料集操作時都會在該表的Timeline上生成一個Instant,進而可以實作在僅查詢某個時間點之後成功送出的資料,或是僅查詢某個時間點之前的資料,有效避免了掃描更大時間範圍的資料。
同時,可以高效的隻查詢更改前的檔案(如在某個Instant送出了更改操作後,僅query某個時間點之前的資料,則仍可以query修改前的資料)
Action:
COMMITS:資料送出
CLEANS:資料删除
DELTA_COMMIT:
COMPACTION:小檔案合并
ROLLBACK:復原
SAVEPOINT:儲存點
Timeline是hudi用來管理送出(commit)的抽象,每個commit都綁定一個固定時間戳,分散到時間線上。
在Timeline上,每個commit被抽象為一個HoodieInstant,一個instant記錄了一次送出(commit)的行為、時間戳和狀态
上圖中采用時間(小時)作為分區字段,從10:00開始陸續産生各種commit,10:20來了一條9:00的資料,該資料仍然可以落到9:00對應的分區,通過timeline直接消費10:00之後的增量更新(隻消費有新commits的group),那麼這條延遲的資料仍然可以被消費到
時間軸的實作類(位于hudi-common-xx.jar中),時間軸相關的實作類位于org.apache.hudi.common.table.timeline包下
2.檔案管理
hudi将DFS上的資料集組織到基本路徑(HodieWriteConfig.BASEPATHPROP)下的目錄結構中
資料集分為多個分區(DataSourceOptions.PARTITIONPATHFIELDOPT_KEY),這些分區與hive表非常相似,是包含該分區的資料檔案的檔案夾
在每個分區内,檔案被組織為檔案組,由檔案ID充當唯一辨別。每個檔案組包含多個檔案切片,其中每個切片包含在某個即時時間的送出/壓縮生成的基本列檔案(.parquet)以及一組日志檔案(.log),該檔案包含自生成基本檔案依賴對基本檔案的插入/更新。
資料構成關系:table -> partition -> FileGroup -> FileSlice -> parquet + log
hudi的base file(parquet檔案)在footer的meta去記錄了record key組成的BloomFilter,用于在file based index的實作中實作高效率的key contains檢測
hudi的log(arvo檔案)是自己編碼的,通過積攢資料buffer以LogBlock為機關寫出,每個LogBlock包含magic number、size、content、footer等資訊,用于資料讀、校驗和過濾