Apache Hudi是一個開源數據湖管理平台,用於簡化增量數據處理和數據管道開發,該平台可以有效地管理業務需求,例如數據生命周期,並提高數據質量。Hudi的一些常見用例是記錄級的插入、更新和刪除、簡化文件管理和近乎實時的數據訪問以及簡化的CDC數據管道開發。
本期SOFTWARE DAILY我們有幸采訪到了Apache Hudi項目VP Vinoth Chandar。Vinoth是Uber Hudi項目的創建者,他繼續在Apache Software Foundation領導Hudi的發展。在此之前他曾是Confluent的首席工程師,之前是Uber的高級工程師/經理。本期我們將討論構建大型分布式和數據系統。
Q1:今天我們就數據湖、數據倉庫和數據基礎設施進行一場引人入勝的討論。數據湖可以低成本存儲所有數據,然后使用該數據執行操作,由於價格便宜,可以保存所有數據。數據倉庫是更昂貴的存儲空間,它可能更接近內存,並且通常更昂貴,但訪問速度更快。這是我如何看待這兩個抽象的非常粗略的描述。我希望您對這兩個抽象以及這些術語在過去幾年中的演變有何看法?
VC:我認為您對它們的描述幾乎與幾年前一樣,如果稍微倒退一點回到Teradata、Vertica時代,存儲與計算耦合的數據倉庫,他們幾乎都是MPP數據庫,然后到Hadoop時代,帶來了水平可擴展的計算能力,然后數據湖和倉庫共存。但是最后我想說大約五年來,數據湖和數據倉庫生態系統都發生了巨大的變化。具體地說,雲數倉現在是黃金時間,它們與以前的倉庫有完全不同的體系結構,它們使存儲和計算分離,然后可以使用雲存儲來水平擴展,這樣它們聽起來就像是數據湖。而如果使用數據湖,那么會有事務性管理數據的需求,或者具有變更和更新存儲在數據湖中的數據的能力。擺脫了"好吧,讓我們將其視為所有數據的廉價轉儲,轉變成更有意識組織的,大量結構化數據流入數據湖",然后數據湖技術也開始變得越來越像數據庫/數據倉庫邊界,從我看來那就是我們的方向。
Q2:您對不同的流行數據倉庫(數據湖抽象)看法是什么? 我看到的三個主要對象是Snowflake,BigQuery和帶有Delta和Spark的Lakehouse架構。也許還會包括Redshift。也許您可以列舉不同的流行數據倉庫,數據湖抽象以及它們之間的對比。
VC:那么讓我們從雲數據倉庫開始,實際上我會將Redshift放在前面,我會將Redshift,BigQuery和Snowflake視為雲數倉。它們都有一些非常共同的特征,如都有很多類似數據庫的參數。實際上它們具有的事務處理能力要遠遠高於您所看到的能力,正如我們在談論數據湖抽象時所看到的,它們都具有一種內部專有格式,不是很開放,並且非常類似於垂直集成系統,包括SQL、文件格式、執行運行時。他們與BI系統緊密集成,就像常規分析一樣,因此我以類似的方式來看待它們。然后進入數據湖,這是我從2016年左右開始涉足Apache Hudi的背景,包括Databricks的Delta Lake,Netflix的Apache iceberg,三個系統都提供了一個事務層,就像在S3或雲對象存儲之上管理文件一樣,並且使用開放文件格式,如Parquet、ORC。這三個項目在內部設計以及解決問題的方式有一些相似之處和不同點。就我個人而言,當Lakehouse出現時,我並不感到驚訝,因為幾年來我們已經在Uber投入生產類似的東西,我知道有幾家大型科技公司已經在做類似的事情,其核心思想是:“讓我們將數倉的原語帶到數據湖,並試圖在數據湖本身上做更多的事情" ,而且我認為Databricks做出了出色的工作,它是業界領先的Spark計算提供商之一,為這種架構模式增加了行業視野,他們在表達這種願景方面也做得很好,這就是我的看法。
Q3:既然您提到Uber,您能給我更多有關Uber的數據倉庫或Uber的數據基礎架構的背景信息嗎?
VC:我在2014年加入Uber,Uber業務增速非常快,這意味着隨着我們推出更多城市,數據量也在不斷增長。Uber是一家非常實時的公司,我們可以通過構建大量針對數據新鮮度進行優化的系統來節省大量資金。公司、城市運營商,工程師,每個人都可以訪問數據。我們從Vertica開始,但是隨着數據量的增長,我們意識到需要一個數據湖,我們使用Spark將所有初始數據轉儲到數據湖中,然后將原始數據從本地倉庫中移出。但是當真正開始實施時,我們意識到在數據庫和數據湖之間增加了額外一層,這導致上在它們之間增加了很多延遲,這主要是由於所有事情都是大批量完成的, Hadoop世界更喜歡大規模批量操作。這就是Hudi出現的背景,需要支持更新,刪除。我們實際上可以獲取數據庫更改日志,這給我們帶來了極大的查詢數據新鮮度,而Vertica也為我們提供了良好的查詢性能。我們通過在Hadoop文件系統抽象之上構建事務層或無服務器事務層來復制類似的東西,以便它可以與HDFS,S3一起使用,這是面向未來的。並且我們嘗試在將操作數據提取到數據湖中的同時解決更新和刪除問題,可以將批處理工作從大約12、16小時,24小時運行轉變為在30分鍾,15分鍾,5分鍾內完成,實際上可以根據我們的需求調整延遲,因為Hudi可以使用Apache Spark作為運行時,因此它可以非常好地水平擴縮容。
我們解決的第二個問題僅僅是解決更新和刪除問題,但還不夠,因為通常在數據湖體系中會擁有一組原始表,然后使用ETL作業從中構建更多派生表,但所有這些派生表都不了解實際更改了哪些數據。例如有一個簡單的ETL作業(正在標准化貨幣換算或某些非常簡單的原始操作),但必須對整個小費表表進行全表掃描,才能真正了解發生了什么變化,所以我們說:“好吧,流處理是如何解決這個問題的",這就是Hudi內置的兩個基本特性。我們在支持更新,刪除和增量更改流的同時也支持了事務,這就是Hudi誕生的方式,我們在2016年做到了這一點。到2016年底,Hudi已經穩定運行兩年時間,為Uber的所有關鍵業務關鍵數據集提供了動力,已經存儲了幾PB的數據。我們在2017年開源了該項目,進入了Apache孵化器,2018年Apache孵化器中畢業。而且我們一直在與許多在其平台上采用Hudi的雲提供商一起發展社區,以解決整個行業廣泛存在的相同問題。
Q4:為何當時沒有像現有的數據基礎架構技術那樣解決這些問題?如今這些現有的數據湖、數據倉庫產品已經解決了這些問題嗎?
VC:我們需要事務、更新和刪除等功能,以便我們快速將數據從上游數據庫中提取到倉庫中。但是倉庫不能容納所有數據,您可以運行數十個節點的Arrows群集,但是我們的數據量巨大,以至於無法容納在任何一個集群中,這是Arrow限制,我們無法進行擴展。
總的來說在Hadoop技術棧體系中,當時還沒有成熟的系統能夠攝取數據並真正很好地對其進行管理。Hadoop計划中的大部分工作都用於構建HDFS,Yarn,Hadoop Spark,Hive Spark,Presto等,實際數據管理或存儲層並未引起太多關注,例如調整文件大小。用戶可以擴展HDFS並通過寫入適當大小的文件來保持HDFS健康,但沒有庫在整個生態系統中統一實現這一功能,大型公司都試圖構建自己的解決方案,但在不同時間軸上,實際這是一個明顯的問題,也是Hudi的誕生方式。如果拉回到今天,我會說雲倉庫在解決我說過的老式數據倉庫中的數據規模問題方面做得很好,它們的存儲位於S3上而不在本地設備上,它們確實解決了數據存儲擴展問題。但是問題仍然在於它們是專有格式,因此如果今天再次進行操作,我仍會重新構建,因為我們不想將公司的所有原始數據鎖定為一種專有格式,Databricks提出的Lakehouse引起了我的共鳴,因為它們不是通用的,在某種意義上說我們需要一流的公民來支持數據科學和機器學習。然后我們希望數據科學家對分析人員用於報告的相同數據建立模型和分析。如果數據在數據倉庫和數據湖中同時存在,那么會遇到大量的數據質量問題。從體系結構上講,我認為讓數據更快進入由Apache Hudi之類的功能驅動的原始數據湖仍然有意義,這樣對於您要執行的任何下游處理開銷都很少。然后您選擇要使用哪種工具整理數據(如果需要)以進行分析。還是有很多其他實時分析工具,比如Druid、Clickhouse等。
Q5:Hudi是一個開源項目,這意味着它廣泛適用。這不僅適用於不同規模的公司。為什么這是一個廣泛適用的問題?
VC:這是一個非常非常好的問題。當我們真正開始創建Hudi時,甚至是在我自己追溯該問題時,我都非常確信這就是我們必須為Uber構建它的方式。人們通常應該采用這種方式,但是並不是那種強制功能可以使人們以某種方式采用這種功能,如果您查看其中的一些技術,Hudi自2016年左右就已經存在,實際上它帶給我們的是GDPR之類的能力,還有諸如強制功能之類的服務,轉儲到S3或其他存儲上的所有數據,您都需要對其進行管理,需要刪除內容,需要糾正或掩蓋其中的內容,這個場景適用於任何跨國公司,然后這也引起了人們對數據湖的大量關注,這就是我們感到Hudi非常適用的地方。以事務方式更新數據,然后像流數據湖模式(如我所說的那樣)進行攝取的技術正在慢慢流行起來,人們意識到在數據隱私法律中需要適當地管理用戶數據,那么什么是正確的架構?看來我需要一個數據湖,現在有了這些工具,我們在該行業上是正確的,而且我認為未來幾年我們將適應各種模式。
Q6:簡單介紹一下您認為理想的數據體系結構。就像什么理想的用戶體驗可以消除大量的配置和繁瑣的設置工作或維護工作? 對於在數據平台之上工作的數據工程師,數據科學團隊來說,什么是好的理想體驗?
VC:這是另一個奇妙的問題,讓我們從組織的角度來思考這個問題,假設有一家公司已經相當成功了,它擁有數百名員工。然后現在數據管理問題開始出現了,然后可以使用一些集成工具來進行基本的報告分析。但現在如果有兩三個業務職能,一個風險團隊,一個風險欺詐團隊,並且有一個財務團隊,還有一個產品團隊,每個團隊都需要聘請數據工程師,並且對用戶某些操作中的數據感興趣,數據在MySQL,Postgres、Oracle、RDBMS或NoSQL存儲,然后會自然引入Kafka消息隊列,像事件跟蹤數據一樣,幾乎每個公司都使用類似的方法來跟蹤許多正在進行的活動。因此大多數公司從本質上選擇了一條途徑,即從聘請數據工程師到各個業務職能部門開始,他們精心挑選所需的數據集,他們實際上並沒有像完全集中的數據湖那樣進行構建,因為在組織上通常很難為這種產品提供資金。隨着時間的流逝,最終出現了數據孤島。然后財務團隊成員寫的查詢無法與欺詐團隊中的某人核對數據,然后需要給財務團隊中的某人(而不是欺詐團隊)一個類似的、不同種類的生產數據訪問控制,使得人們抱怨在使用數據湖的痛苦,我認為要解決的首要問題是在原始環境中將大量上游系統復制到數據湖中,這必須在沒有太多轉換的情況下進行,而且它必須非常快地完成操作,這樣您就可以在工作之前不必等待數小時才能收到這些數據了,因此只要您能夠像原始數據流一樣構建它們稱為的原始數據層,然后將其釋放-並在其之上使用一些類似的工具和控件訪問控制,那么它將使您的數據工程師專注於業務功能,如果他們想連接某些表以獲得更好的數據質量也很容易做到,因為他們擁有所有可用的數據。如果您今天看一下Databricks,Databricks是一個Spark運行時,其提供了大量數據科學工具,而且如果您查看的是Starburst或Presto,HANA Starburst,Presto之類的查詢引擎公司,它們確實非常適合–就像他們擁有良好的BI工具一樣,實際上可以根據用例選擇要使用的查詢引擎,並且可以向數據科學團隊提供數據庫訂閱,當財務團隊運行報表時,就像儀表板一樣。因此可以自由選擇,並且可以實際控制哪些數據,回到我之前說的那樣,此原始原始數據層幾乎沒有增加數據延遲,所有原始數據都非常快地流入數據湖,這就是在公司中進行的任何派生數據計算的起點。您可以隨時從一個雲倉庫轉移到另一個倉庫,也可以像您喜歡的那樣引入或淘汰舊的實時分析引擎。如果需要您將幾乎可以重新計算任何東西,並且此模型具有很大的自由度,我認為這就是我應該朝着的方向發展。
Q7:鑒於您剛剛將其描述的未來,請描述下數據基礎架構部署到該世界需要做些什么?還是我們需要在基礎設施技術方面取得哪些進步才能實現這一未來?
VC:我認為很多技術已經存在,如果我們現在一步步走,首先我們需要做的事情就是真正捕獲更改數據–這就是類似Debezium這樣的項目做得很棒的地方,越來越多的公司從數據庫提供CDC流,而且隨着這種方式成為主流,采用更加標准化的工具來獲取這些流並將其放入數據湖的表中,我認為這是我們真正需要的。有了Apache Hudi,我們已經朝這個方向邁出了一大步,這就像我們一直在構建Hudi一樣,就像一個平台,而不是像事務層一樣,或者只解決了這一更新問題,更多的工具和一條更好的途徑來快速地提取和集成數據,我要說的第二部分是如果花一點時間來比較一下雲數據倉庫和數據湖,數據湖中的中央meta存儲可能仍然是Hive Metastore,然后在最近幾年,Hive Metastore有其自身的可擴展性問題,它無法跟蹤文件級別或類似級別的詳細統計信息,因此我覺得我們需要為了使人們能夠以出色的性能查詢此數據並希望提供出色的可用性,我們需要要么像Hive Metastore這樣的顯着改進,要么像Hudi這樣的新型類似系統以及為開源查詢引擎抽象的類似系統,這是我看到的一個技術差距。如果沒有此功能,則您的Presto查詢引擎可能真的非常非常好,但是如果沒有所有統計數據輸入,您將無法獲得與像雲數據倉庫這樣的完全垂直集成的系統一樣的性能,所以這些都是我認為我們需要改進的地方。
我要說的第三點,實際上是Hudi目標的核心,作為一個項目我們要思考的要比我們做的要遠得多,我們必須想一想如何從流處理中學習並讓我們的批處理作業更多,如增量運行無需過多處理,因為任何時候您都會遇到圍繞數據新鮮度或查詢性能的類似瓶頸,這會導致就像我們剛剛討論過的理想數據架構面臨的風險和威脅一樣。從那時起人們開始采用捷徑,並且喜歡在其數據體系結構方面朝着不同的方向發展,我認為這是我們應該建立的三件事。
Q8:回到Apache Hudi,您可以更深入地介紹Hudi的體系結構嗎?
VC:從高層次上講對Hudi最好的描述是它是一個數據湖平台,而且它有很多平台組件,它們圍繞某種數據庫核心進行了構建,並針對流處理進行了優化,所以我喜歡將其分解,Hudi是一個庫,沒有長期運行的服務器,用戶可以使用Spark或Flink向其中寫入數據。Hudi將類似的數據組織在Apache Parquet或Apache Avro文件中,並且提供了很多元數據,還跟蹤有關在雲存儲上對該邏輯數據集進行的寫入和更改的大量元數據,然后所有查詢引擎(例如Hive,Spark,Presto,Impala,Trino甚至Redshift)都可以直接查詢在Hudi表中寫入的數據。現在如果像Hudi OSI數據層那樣分解Hudi,那么您就擁有了雲存儲,此外還有這些開放數據文件格式,Parque,ORC,Avro文件格式以及所有內容,Hudi定義了文件組織的布局,然后再提供並發控制和事務。然后它提供了一些功能來對數據建立索引,以便您可以進行快速更新刪除,另外Hudi還有一些服務(守護程序)優化存儲布局,並在用戶高興地只是將數據寫入格式時在后台重新索引某些內容,壓縮或在后台執行多項操作,Hudi有很多這樣的服務,它們可以在寫入過程中同步運行或者異步運行。它們可以像優化所有表的守護程序一樣運行。對於更新操作,可以先增量更新到日志中,然后再壓縮它們,因此有一個壓縮服務,當然用戶可以改變數據存儲布局,並重新對數據進行聚類以獲得更好的查詢性能,因此Hudi有一個Clustering服務,然后還有個Clean服務清理和清除舊文件,所有這些服務彼此協調,這是Hudi的核心設計,而不是像其他系統那樣,Hudi有大量的上層服務,就像有一個提取服務一樣,它可以從Kafka中獲取數據,將其轉換為本質上是流,而不只是在S3上的Hudi表,它可以執行檢查點管理,它可以自己進行恢復。同樣我們擁有一堆不同的非結構化數據格式進行轉化將其提取到Hudi表中;也可以編寫流式的增量ETL管道,僅從上游Hudi表中使用變更流,可以獲得自某個時間點以來已插入或更新的所有記錄。Hudi也可處理重復數據。另外我們提供了一些工具,可以在數據寫入Hudi表時對外提供通知,我們有很多這樣的服務,這就是為什么我要說我們的原則不是要建立一個數據庫核心,而是要建立一套工具和服務,使人們可以簡單地使用它,然后解決實際問題。
Q9:如果系統可以從Hudi受益但沒有使用Hudi,它們將面臨哪些挑戰呢?
VC:讓我們來一個沒有Hudi的數據湖。包括一個上游數據庫,假設您有一個Cassandra集群或Dynamo,例如某些數據庫,其中包含一些即將到來的變更流,您有一個Kafka集群,您的微服務通過該集群記錄事件。現在您已經擁有了我們想要構建的數據湖體系結構。但是您想構建一組原始表,然后編寫一些ETL並構建一種派生表,如果沒有Hudi,人們通常會這樣做,那就是他們會像Spark作業那樣編寫代碼,或者使用Kafka Connect或Camel之類的框架或者只是繼續編寫某些內容–就像從Kafka提取一樣,將這些事件寫成類似Avro文件和行存,這就是您布置原始數據的方式。然后他們將在幾個小時內批量導入數據庫,或者可以從這些數據庫中進行更改捕獲,但是他們不知道如何應用它們,因此他們需要對整個表進行批量合並,這會進行數據庫的大量提取,並且它們將像事件的增量式提取那樣進行。而且如果他們想每5分鍾或每1分鍾提取一次Kafka數據,他們就必須做更多的事情來控制文件大小和所有內容,這導致原始層中數據庫數據的數據新鮮度較差,並且產生有很多小文件,或者由於它們是基於行的格式,導致分析查詢性能差。同樣編寫ETL的作業也將延遲,通常您使用Hive或Spark編寫一堆ETL,然后構建一組派生數據表,這些導出的數據表還遭受不良的數據新鮮度的困擾,原始數據的查詢效率也非常非常差,因為您必須應對原始數據格式,並且必須處理許多小文件,這些文件通常會降低查詢性能。如果使用Hudi之類的工具,便可以使用Hudi的增量數據流工具,如果某個Kafka集群中有任何數據,則可以增量、連續攝取,同時可以直接使該表,這意味着即使是數據庫數據,數據延遲也在幾分鍾之內。同時還可以使用Hudi自動調整小文件功能,以便下游ETL和查詢執行性能更好,因為采用列存格式。
以Uber為例說明,如果每30分鍾提取一次數據,將會寫入10個文件,這10個文件中的大多數將包含所有城市的數據,因為這有點像數據到達的方式。但通過類似Hudi Clustering的服務可以重組數據,使屬於給定城市的所有記錄彼此靠近。這樣一來查詢實際上掃描的數據量將大大減少。可以做很多事情來減少查詢成本,提高效率,還可以很好地改善數據的新鮮度,繼續到派生的數據管道,Hudi還可以提供Hudi中每個表的變更流,這意味着可以采用與流處理中相同的概念。同樣您可以像Flink或Spark作業那樣將變更流連接到Hudi表,它也可以作為快照與另一個Hudi表關聯查詢。編寫增量數據管道使得它們處理較少的數據量,這意味着成本較低,並提供了更好的數據新鮮度,這是我想當初在Uber進行的一件令我着迷的事情。通常您沒有機會獲得可以真正降低成本並且在構建數據庫時也可以更快的機會,Hudi為您提供了一個框架,使您可以實際增量地攝取和增量地執行ETL,簡而言之它將為您的數據湖做好准備。
Q10:那么對於Hudi來說,由Hudi構建的所有東西都被放入內存了嗎,還是Hudi完全使用磁盤?
VC:當您查詢Hudi表時,它與查詢Hive表或Presto表沒有什么不同,或像為Hive表一樣,本質上這些湖引擎所做的就是Hudi所做的。 Hudi就像查詢層的形式一樣,只是像它們查詢的表抽象一樣呈現,Hudi本身會將所有數據存儲在雲存儲之上,它沒有任何長時間運行的內存組件。在執行期間它可能會在給定的事務中緩存一些內容,僅此而已。
Q11:那么應用程序所有者(例如正在查詢的人)還是正在像數據科學家一樣進行最終查詢的人,他們是否需要了Hudi?還是對他們透明?
VC:如果他們正在執行批處理查詢,例如,如果您只是查詢表的快照,那么它們通常不必真正關心它是Hudi還是Delta Lake或其他任何格式,甚至是Hive,他們通常只是簡單地感興趣:"查詢速度更快,數據正確",就這樣。因此他們不必知道,但是如果您是寫增量ETL的數據工程師,那么您需要利用非常特定於Hudi的功能,您需要了解Hudi格式是什么,因此這些人可能會意識到,如果您正在編寫批處理ETL管道,您甚至都不知道它是否是Hudi表,它的行為就像其他任何Hive表一樣。
Q12:當我們結束對話時,我想和您一起探索更多的東西。但是請描述現在Hudi的狀態,它能做什么?您希望該項目實現的願景是什么?距離您那個願景有多遠?
VC:廣義上講有很多原因,Hudi是我們2016年分享的願景的體現,"所有批處理都應該是增量的",通過Hudi,我們在鞏固這一目標方面取得了很大進展。當集成原始數據層的數據時需要以增量的方式進行處理,我們在Hudi中構建了許多出色的軟件堆棧,它們的性能可能非常出色,並且具有許多功能可以使您做到這一點。具體地說我們有一個數據庫核心和一組類似的服務,這些服務都可以水平擴展和輕松部署。如果您知道如何部署Spark作業和Flink作業,Hudi可以開箱即用。我們將來真正想投資的部分實際上正在釋放真正的端到端增量ETL管道,我們應該能夠編寫非常復雜的ETL管道。批處理非常簡單,它是無狀態的。然而今天的流處理是有狀態的,甚至需要像一套不同的工程師一樣來編寫非常好的流處理程序,因此我們實際上希望降低該標准,然后幫助人們編寫復雜的增量ETL作業,並為該模型增加更多的批處理ETL工作量,就像我們希望該項目達到目標一樣,另一部分是我們需要在項目中解決的另一件事,我們正在逐步進行所有工作,因為我們希望節省成本,並且希望數據新鮮度更高,但是查詢引擎側還有很多空白,雲存儲系統的一些基本限制可能會影響這些新數據的實時查詢性能,因此這有兩個方面。數據延遲我們可以通過增量ETL和增量攝取來解決,但是交互式和類似實時分析查詢的性能是我們可能需要構建的東西,例如Hudi中的可變緩存,列式緩存層,它實際上可以吸收大量更新,將其保存在內存中,降低了合並成本,以便人們可以很好地對其進行查詢,現在所有表統計信息都寫在一個JSON文件和Avro文件中,這就像可伸縮性一樣,但是用這種方式計划查詢可能會花費大量時間。因此我認為一個高性能和高度可伸縮的元存儲,內部有Snowflake或BigQuery或redshift之類的東西,我們需要構建類似的東西,我認為將這兩者放在一起將真正釋放我們的願景,那就是所有數據都應該非常快地到達,並且也應該能夠很快被查詢。