快手自研Spark向量化引擎正式發(fā)布,性能提升200% 原創(chuàng)
Blaze 是快手自研的基于Rust語言和DataFusion框架開發(fā)的Spark向量化執(zhí)行引擎,旨在通過本機(jī)矢量化執(zhí)行技術(shù)來加速Spark SQL的查詢處理。Blaze在快手內(nèi)部上線的數(shù)倉生產(chǎn)作業(yè)也觀測到了平均30%的算力提升,實現(xiàn)了較大的降本增效。本文將深入剖析blaze的技術(shù)原理、實現(xiàn)細(xì)節(jié)及在快手實際生產(chǎn)環(huán)境中的真實表現(xiàn)。
一、研究背景
當(dāng)下,Spark 的重要發(fā)展方向之一是通過向量化執(zhí)行進(jìn)一步提升性能。向量化執(zhí)行的思想是將算子的執(zhí)行粒度從每次處理一行變成每次處理一個行組,以此來避免大量的函數(shù)調(diào)用。通過對行組內(nèi)部處理按列進(jìn)行計算,同時利用編譯技術(shù)減少分支判斷檢查以及更多的 SIMD 優(yōu)化執(zhí)行計劃。
Blaze 是快手自研的基于Rust語言和DataFusion框架開發(fā)的Spark向量化執(zhí)行引擎,旨在通過本機(jī)矢量化執(zhí)行技術(shù)來加速Spark SQL的查詢處理。在性能方面,Blaze展現(xiàn)出顯著的優(yōu)勢:在TPC-DS 1TB的測試中,Blaze相較于Spark 3.3版本減少了60%的計算時間、Spark 3.5版本減少了40%的計算時間,并大幅降低了集群資源的消耗;此外,Blaze在快手內(nèi)部上線的數(shù)倉生產(chǎn)作業(yè)也觀測到了平均30%的算力提升,實現(xiàn)了較大幅度的降本增效。
如今,Blaze已開源,擁抱更廣闊的開發(fā)者社區(qū)。開源版本全面兼容Spark 3.0~3.5,用戶能夠輕松集成Blaze至現(xiàn)有Spark環(huán)境中,僅需簡單添加Jar包,即可解鎖Blaze帶來的極致性能優(yōu)化,享受前所未有的數(shù)據(jù)處理速度與資源效率。
Github地址: https://github.com/kwai/blaze
二、Blaze的整體架構(gòu)及核心
Spark on Blaze架構(gòu)的整體流向
Spark+Blaze 的架構(gòu)設(shè)計原理如下圖:
對比Spark原生的執(zhí)行流程,引入Blaze Session Extension組件所帶來的作用是顯著的,特別是在提升數(shù)據(jù)處理效率和性能方面。
Spark原生執(zhí)行流程主要依賴于Java虛擬機(jī)(JVM)進(jìn)行任務(wù)的執(zhí)行,盡管JVM在提供跨平臺、內(nèi)存管理等方面有著卓越的表現(xiàn),但在大數(shù)據(jù)處理場景下,尤其是涉及大規(guī)模數(shù)據(jù)計算和復(fù)雜查詢時,JVM的性能開銷可能會成為瓶頸。
Blaze Session Extension組件的引入,巧妙地解決了這一問題。該組件在Spark生成物理執(zhí)行計劃之后介入,通過其翻譯邏輯將這一計劃轉(zhuǎn)換為等效的、native向量化引擎可以識別的形式,隨后提交到Executor端由native引擎執(zhí)行計算,從而實現(xiàn)了數(shù)據(jù)處理效率的飛躍。
而這一切的背后,離不開Native向量化引擎這一核心模塊的支持。該引擎由Rust語言實現(xiàn),憑借其卓越的性能、安全性和并發(fā)處理能力,成功實現(xiàn)了Spark中大多數(shù)關(guān)鍵算子的等效替代,包括但不限于Project、Filter、Sort等。這些經(jīng)過優(yōu)化的算子在執(zhí)行過程中,通過向量化技術(shù)顯著提升了計算效率,使得數(shù)據(jù)處理過程更加流暢、快速。
四大核心組件
Blaze 架構(gòu)中的核心模塊有四個,共同驅(qū)動著大數(shù)據(jù)性能的顯著提升。這些模塊分別為:
- Native Engine:基于 Datafusion 框架實現(xiàn)的與 Spark 功能一致的 Native 算子,以及相關(guān)內(nèi)存管理、FFI 交互等功能。
- ProtoBuf:定義用于 JVM 和 native 之間的算子描述協(xié)議,對 Datafusion 執(zhí)行計劃進(jìn)行序列化和反序列化。
- JNI Bridge:實現(xiàn) Spark Extension 和 Native Engine 之間的互相調(diào)用。
- Spark Extension:Spark 插件,實現(xiàn) Spark 算子到 Native 算子之間的翻譯。
具體的執(zhí)行過程中,遵循以下步驟:
物理執(zhí)行計劃的轉(zhuǎn)換:首先,Spark Extension將 Spark 生成的物理執(zhí)行計劃轉(zhuǎn)換為對應(yīng)的 Native Plan;
生成和提交Native Plan:轉(zhuǎn)換完成后,Native Plan通過JNI Bridge被提交給Native Engine進(jìn)行進(jìn)一步的處理。
Native 執(zhí)行層:最后,Native Engine利用其高效的內(nèi)存管理機(jī)制和向量化處理技術(shù),對Native Plan進(jìn)行真正的執(zhí)行。執(zhí)行結(jié)果通過JNI Bridge返回給Spark,從而完成整個數(shù)據(jù)處理流程。
三、Blaze的技術(shù)優(yōu)勢:面向生產(chǎn)的深度優(yōu)化
在跑通 tpch 和 tpcds 測試集并取得預(yù)期性能提升后,我們面向線上生產(chǎn)環(huán)境進(jìn)一步做了系列深度優(yōu)化,包括性能和穩(wěn)定性等方面工作:
細(xì)粒度的FailBack機(jī)制
我們針對Spark執(zhí)行效率的提升,設(shè)計并實現(xiàn)了演進(jìn)式向量化執(zhí)行方案。這一方案旨在逐步優(yōu)化算子與表達(dá)式的向量化覆蓋,同時解決Java UDF無法直接轉(zhuǎn)化為Native執(zhí)行的問題。通過引入細(xì)粒度的FailBack機(jī)制,Blaze在翻譯過程中遇到暫無Native實現(xiàn)的算子、單個表達(dá)式或UDF時,支持算子/單個表達(dá)式粒度的回退,能夠靈活回退到Spark原生執(zhí)行。此機(jī)制首先確定算子/表達(dá)式的依賴參數(shù)列,利用Arrow FFI技術(shù)將這些參數(shù)列作為行傳遞給Spark進(jìn)行處理,然后將結(jié)果以列的形式回傳至Blaze,從而在JVM與Native執(zhí)行之間構(gòu)建了一座橋梁。
此方案不僅加速了向量化執(zhí)行的全面部署,還確保了即便在用戶SQL中有少量UDF等不支持的場景,細(xì)粒度回退單個表達(dá)式開銷較小,作業(yè)整體依然可以得到優(yōu)化。
更高效的向量化數(shù)據(jù)傳輸格式
在Spark中,Shuffle操作因其復(fù)雜的數(shù)據(jù)流轉(zhuǎn)過程成為性能瓶頸,涉及編碼、壓縮、網(wǎng)絡(luò)傳輸、解壓及解碼等多個環(huán)節(jié)。原生Spark采用基于行的序列化與壓縮方式,而業(yè)界向量化數(shù)據(jù)則傾向于Arrow格式傳輸,但實踐中發(fā)現(xiàn)Arrow與主流輕量壓縮算法適配不佳,導(dǎo)致壓縮率低下且存在冗余信息。針對此問題,Blaze定制了優(yōu)化的數(shù)據(jù)傳輸格式,不僅去除了列名、數(shù)據(jù)類型等冗余數(shù)據(jù),還使用了byte-transpose列式數(shù)據(jù)序列化技術(shù),通過重組整型/浮點型數(shù)據(jù)的字節(jié)順序,顯著提升數(shù)據(jù)壓縮效率。這一改進(jìn)大幅減少了Shuffle過程中的數(shù)據(jù)傳輸量,并在實際測試與TPC-DS基準(zhǔn)測試中展現(xiàn)出顯著的性能提升與資源消耗降低,有效解決了原有問題并優(yōu)化了系統(tǒng)整體性能。
::: hljs-center
線上2000多個作業(yè)的真實數(shù)據(jù),上線后輸入數(shù)據(jù)量小幅上漲的情況下,Shuffle數(shù)據(jù)量相比spark降近30%
:::
減少用戶成本的多級內(nèi)容管理策略
面對Spark與Native執(zhí)行模式在內(nèi)存管理上的差異,我們設(shè)計了跨堆內(nèi)堆外的自適應(yīng)內(nèi)存管理機(jī)制。該機(jī)制根據(jù)任務(wù)的向量化覆蓋情況智能調(diào)整內(nèi)存分配,確保資源高效利用。同時,我們構(gòu)建了堆外內(nèi)存、堆內(nèi)內(nèi)存與磁盤文件之間的多級管理體系,有效防止了內(nèi)存不足及頻繁數(shù)據(jù)溢寫的問題。這些措施不僅保障了向量化引擎上線后任務(wù)的穩(wěn)定運行,無需用戶手動調(diào)整內(nèi)存參數(shù),大幅降低了用戶操作成本,提升了整體系統(tǒng)的易用性與可靠性。
復(fù)雜度更優(yōu)的聚合算法實現(xiàn)
為深度適配Spark的復(fù)雜需求,Blaze在aggregate、sort、shuffle等關(guān)鍵算子的實現(xiàn)上并未直接采用DataFusion的現(xiàn)成方案,而是進(jìn)行了定制化開發(fā)。以HashAggregate為例,當(dāng)面對大規(guī)模group-by聚合且內(nèi)存不足時,Spark會轉(zhuǎn)而采用基于排序的聚合,這涉及高復(fù)雜度的排序與歸并過程。而在Blaze中,我們采用了基于分桶的歸并方式,利用基數(shù)排序在spill時進(jìn)行分桶、溢寫,并在合并階段通過hash 表快速合并,整個流程保持O(n)的復(fù)雜度,顯著提升了聚合算子的執(zhí)行效率與資源利用率。
向量化計算場景的表達(dá)式重復(fù)計算優(yōu)化
針對SQL執(zhí)行中算子間常見的重復(fù)表達(dá)式計算問題,Blaze借鑒了Spark的Whole-stage codegen技術(shù),應(yīng)用了這一項優(yōu)化策略。該策略能夠智能識別并合并包含重復(fù)表達(dá)式的算子,如下圖中的Project與Filter合并為一個大算子,并在其中對表達(dá)式計算結(jié)果進(jìn)行緩存、復(fù)用,達(dá)到了減少重復(fù)計算、提高執(zhí)行效率的目的。這一優(yōu)化在應(yīng)對復(fù)雜計算邏輯(如JSON解析多個字段、UDF調(diào)用)時尤為顯著,能將執(zhí)行效率提升一倍以上。特別是在內(nèi)部業(yè)務(wù)場景中,對于高頻調(diào)用的重負(fù)載UDF,該優(yōu)化成功減少了約40%的計算開銷,顯著增強(qiáng)了系統(tǒng)的整體性能與響應(yīng)速度。
四、當(dāng)前進(jìn)展及未來規(guī)劃
當(dāng)前進(jìn)展
Blaze 作為一款高性能數(shù)據(jù)處理引擎,已取得了顯著進(jìn)展,全面支持多項核心功能,展現(xiàn)出強(qiáng)大的技術(shù)實力與廣泛的應(yīng)用潛力。具體而言,Blaze 目前已具備以下關(guān)鍵能力:
- Parquet向量化讀寫能力:實現(xiàn)了對Parquet格式數(shù)據(jù)的高效向量化讀寫,極大地提升了數(shù)據(jù)處理的速度與效率。
- 全面算子與表達(dá)式支持:覆蓋了線上常用的所有算子與表達(dá)式,少量不支持的表達(dá)式和UDF也可以細(xì)粒度回退,確保用戶能夠無縫遷移并享受向量化處理帶來的性能提升。
- Remote Shuffle Service集成:內(nèi)部集成了自研的Remote Shuffle Service,同時我們也在和阿里合作,增加對Apache Celeborn 的支持,預(yù)計9月份可以提交到社區(qū)。
- TPC-H/TPC-DS測試優(yōu)異表現(xiàn):在業(yè)界權(quán)威的TPC-H/TPC-DS基準(zhǔn)測試中,Blaze成功通過全部測試場景,并以TPC-H平均3倍以上、TPC-DS 2.5倍的性能提升展示了其在復(fù)雜查詢處理上的卓越能力。
在真實的生產(chǎn)環(huán)境中,向量化引擎大規(guī)模上線應(yīng)用,算力平均提升 30%+,成本節(jié)約年化數(shù)千萬元。
未來規(guī)劃
1、持續(xù)迭代優(yōu)化,內(nèi)部線上推全:通過不斷收集用戶反饋與性能數(shù)據(jù),我們將精準(zhǔn)定位并修復(fù)潛在問題,同時引入更多先進(jìn)的算法與優(yōu)化策略,以進(jìn)一步提升Blaze的性能與穩(wěn)定性。
2、支持更多引擎或場景,例如數(shù)據(jù)湖等:為了滿足用戶日益多樣化的數(shù)據(jù)處理需求,我們將不斷拓展Blaze的應(yīng)用場景,支持更多類型的數(shù)據(jù)處理引擎與場景,如數(shù)據(jù)湖等。通過加強(qiáng)與業(yè)界主流技術(shù)的兼容性,我們將為用戶提供更加靈活、便捷的數(shù)據(jù)處理方案,助力用戶解鎖數(shù)據(jù)價值,推動業(yè)務(wù)創(chuàng)新與發(fā)展。
3、加強(qiáng)開源社區(qū)運營建設(shè),共建生態(tài)繁榮:我們深知開源社區(qū)對于技術(shù)發(fā)展與生態(tài)繁榮的重要性。因此,我們將在之后加強(qiáng)Blaze開源社區(qū)的運營建設(shè),積極構(gòu)建一個開放、包容、協(xié)作的社區(qū)環(huán)境。當(dāng)前我們已經(jīng)與阿里、B站、攜程、聯(lián)通云等公司達(dá)成合作。
如果您對該項目感興趣,歡迎您為項目點個star。
項目地址:https://github.com/kwai/blaze
本文作者:快手技術(shù)王磊
