為什麼不能使用 datax 直接讀寫 hive acid 事務表?
1. 前言
從技術發展趨勢的角度來看,ACID事務表提供了多種新特性新功能,是 HIVE社群推薦的HIVE表格式,且在 CDH/CDP/TDH 等大資料平台的主流版本中均已經提供了支援。
在次背景下,目前我司大資料相關産品和項目,已經在部分場景下開始了探索使用 HIVE ACID事務表。
在此跟大家分享一個 HIVE ACID 事務表的相關問題,希望對大家有所幫助。
2. 從一個 HIVE SQL 報錯聊起
某線上 HIVE SQL 應用,關聯查詢多個事務表時報錯,報錯資訊如下:
~~~java
ERROR : FAILED: Execution Error, return code 3 from org.apache.hadoop.hive.ql.exec.spark.SparkTask. Spark job failed due to task failures: [Error 30022]: Must use HiveInputFormat to read ACID tables (set hive.input.format=org.apache.hadoop.hive.ql.io.HiveInputFormat)
INFO : Completed executing command(queryId=hive_20220606152200_54458918-d42c-445e-8e87-96f75eaeb22f); Time taken: 27.143 seconds
Error: Error while processing statement: FAILED: Execution Error, return code 3 from org.apache.hadoop.hive.ql.exec.spark.SparkTask. Spark job failed due to task failures: [Error 30022]: Must use HiveInputFormat to read ACID tables (set hive.input.format=org.apache.hadoop.hive.ql.io.HiveInputFormat) (state=42000,code=3)
~~~
3. “Must use HiveInputFormat to read ACID tables” 報錯的底層原因
經排查發現,上述事務表底層的ORC 檔案是使用 datax 直接同步過來的,而事務表對表底層在存儲系統中的檔案目錄層次結構,檔案名,以及檔案格式,都有一套自己的規範,使用datax直接同步檔案一般肯定會違反該規範,在後續查詢使用時就會出現各種奇怪的問題,是以不能使用 datax 直接同步資料到事務表對應的hdfs目錄下。
4. HIVE ACID 事務表的技術細節
4.1 首先是檔案目錄層次結構規範
- 每個表或表分區對應一個 HDFS 目錄;
- 表或表分區目錄底層又包含兩類子目錄,一類是 base 子目錄,一類是 delta 子目錄;
- 表或表分區的大部分資料,都以檔案形式存儲在 base 子目錄下;
- 每次對表或表分區的增删改操作,都對應一個事務,都會建立一個對應的 delta 子目錄,并将這些增量操作産生的資料,以檔案形式存儲在該 delta 子目錄下;
- 讀取表或表分區資料時,會合并 base 子目錄和 delta子目錄下的所有檔案,以呈現完整的資料;
4.2 其次是檔案名規範
- 表底層BASE子目錄名稱類似 base_0000003_v0011148,其中中間部分對應建立該子目錄的事務操作的TransactionId;
- 表底層DELTA 子目錄名稱類似(對應 insert/update操作): delta_0000001_0000003_ v0011147,其中中間兩部分對應建立該子目錄的事務操作的最小和最大TransactionId;(insert/update操作生成的delta檔案的最小和最大TransactionId是一緻的,compaction操作生成的 delta檔案的最小和最大TransactionId分别對應 compaction的一系列 delta檔案的最小和最大TransactionId);
- 表底層DELTA 子目錄名稱類似(對應 delete操作):delete_delta_0000001_0000003_ v0011147,其中中間兩部分對應建立該子目錄的事務操作的最小和最大TransactionId;(delete操作生成的delete_delta檔案的最小和最大TransactionId是一緻的,compaction操作生成的 delta檔案的最小和最大TransactionId分别對應 compaction的一系列 delete_delta檔案的最小和最大TransactionId);
- 子目錄底層的檔案名,類似bucket_00000或bucket_00000_0;(不管表是否分桶,檔案名都是該格式;hive2.x和hive3.x新舊版本檔案名格式略有不同)
4.3 最後是檔案格式規範
- ACID事務表底層的檔案,都是以 orc 格式存儲的;
- ORC 檔案包含的字段,除了ACID事務表中正常的業務字段,還包含5個中繼資料字段:operation:int,originalTransaction:bigint,bucket:int,rowId:bigint,currentTransaction:bigint