美團存儲雲原生探索和實踐

本文根據楊立明老師在【第十三屆中國數據庫技術大會(DTCC2022)】線上演講內容整理而成。

本文摘要:存儲計算分離架構是雲原生技術在業務落地的底層重要支撐技術之一,本次分享將介紹美團基礎技術部存儲團隊在存儲計算分離架構上的一些探索,重點是介紹美團的分佈式存儲底座 MStore 的技術架構,以及基於 MStore 建設其他 PaaS 組件和業務系統的一些思考和實踐,幫助業務系統實現存儲計算分離架構的落地,提升整體系統的擴展能力。

雲原生簡述

雲原生技術使組織能夠在新式動態環境(如公有云、私有云和混合雲)中構建和運行可縮放的應用程序。容器、服務網格、微服務、不可變基礎結構和聲明性 API 便是此方法的範例。

這些技術實現了可復原、可管理且可觀察的鬆散耦合系統。它們與強大的自動化相結合,使工程師能夠在儘量減少工作量的情況下,以可預測的方式頻繁地進行具有重大影響力的更改。——“雲原生計算基金會”

總結來說,雲原生技術具有敏捷性、靈活性、可靠性、可伸縮等特點,爲企業提供了巨大的生產力,這也是公司近幾年基礎架構的迭代方向。

存儲計算分離與雲原生

當前,美團基礎架構爲存算一體架構,存儲系統正面臨如下問題:

存儲擴展能力弱:在計算資源達到瓶頸需要擴容時,仍然需要遷移數據,遷移數據的時間跟數據量線性相關,所以,對於數據量較大的業務,擴容操作時間會很長。

機器成本高:存儲計算資源耦合在一起,如果集羣因爲 CPU 計算能力達到瓶頸,我們就需要擴容,而往往這時節點的硬盤空間還很空閒。反之亦然,存儲和計算資源經常會有一方存在機器資源浪費。

重複研發和運維成本高:這些存儲組件基本上要考慮副本冗餘、副本數據一致性、數據正確性校驗,副本缺失補副本,擴容縮容等問題,因此存在着重複研發和運維問題。

不能很好的滿足業務多樣化需求:比如我們現在需要提供一個分佈式文件系統服務,基本上我們需要從零開始研發,研發進度會很慢,不能很好的滿足業務的需要。

以上這些問題阻礙了公司雲原生的建設,因此,我們設計並建設了存儲與計算分離的系統,來更好的滿足雲原生的迭代。

存算分離架構的優勢和挑戰

優勢

擴展能力強:上層存儲服務模塊實現無狀態化設計,可實現秒級擴縮容,無需數據遷移。

產品快速迭代:基於底座,可以最大程度複用其通用存儲能力,來適應業務需求,快速開發出新的存儲產品

降本增效:存儲計算分離,避免了集羣的存儲、計算資源錯配造成的資源浪費。統一底座服務使得上層存儲無需重複研發數據分佈、副本、容災等機制,大幅降低研發成本。

挑戰:

穩定性:作爲其他存儲底層的底座存儲,一旦出現穩定性問題,將會影響其他所有存儲服務,進而影響到上層業務。

性能:分層架構後,相對於存算一體的服務,增加了一跳的網絡延遲。存儲底座的吞吐很大程度上也決定了上層存儲服務的吞吐。

Mstore 總體介紹

針對上述優勢和挑戰,最終我們採用了分佈式存儲底座 MStore 的技術架構。MStore 設計目標是爲各種存儲服務抽象出公共底座,提供似 Posix 的簡單文件接口,對接塊存儲系統、文件存儲系統、對象存儲、表格存儲、數據庫、大數據等業務。

Mstore 整體架構

MStore 存儲系統有 4 個子系統:RootServer、MetaServer、ChunkServer、SDK。

RootServer:集羣的入口,管理着整個集羣中資源信息,包括 MetaServer、ChunkServer、磁盤等信息。

MetaServer:管理着用戶數據的元信息,包括 Blob、Blob 由哪些 Chunk 構成,Chunk 和 ChunkServer 的映射關係等。MetaServer 在集羣中可以有多組,使得元信息管理能水平擴展。

ChunkServer:用戶數據存儲服務,對用戶數據的序列化存儲、校驗。接受用戶讀寫請求,接受 MetaServer 數據複製、負載均衡等請求。

SDK:提供給用戶的 Library,用戶可以通過鏈接這個 Library 訪問 MStore 的存儲服務,類文件系統 API。

Mstore 的 Blob

Blob 是 Mstore 提供給用戶使用的對象,類似於文件。Blob 是由多個 Chunk 組成,以便將 Blob 做分佈式存儲,Chunk 的大小默認爲 64M。

爲了滿足不用的應用場景,目前我們提供兩種類型的 Blob,LogBlob 用於支持追加寫、ExtentBlob 用於支持隨機寫。系統通常是將數據寫到 LogBlob,然後後臺回刷到 ExtentBlob。

Mstore 元數據

元數據主要分爲兩類:資源信息和用戶數據。RootServer 管理所有的硬件資源,整個集羣只有一組。MetaServer 管理用戶數據,可以有多組,可以水平擴展。元數據節點通過 Raft 機制保證數據的可靠性、高可用。

Mstore 資源管理

集羣資源由 RootServer(RS)統一管理,RS 是資源增刪和分配的入口。主要的資源信息包括:MetaServer 組信息、ChunkServer 信息、磁盤信息、PhysicalPool 信息、LogicalPool 信息。

Mstore 資源控制

PhysicalPool 是物理磁盤的集合,一個集羣可以包含多個物理 Pool,一般一個 Pool 中的資源規格是一樣的。

LogicalPool 是對物理資源上的邏輯劃分,一個物理 Pool 中可以創建多個邏輯 Pool。

LogicalPool 概念是暴露給用戶的,用戶可以根據自己的需要對業務做邏輯 Pool 的劃分。

LogicalPool 爲單位定義 QoS,包括服務能力的上限、下限、權重等。

Mstore 用戶數據

用戶數據,需要 MetaServer 決定放置在哪塊盤上,放置策略需要考慮的因素主要有:保證一個 rack 只能有一個副本,寫本地一份,遠程多份的需求,機器和磁盤容量大小,同城多機房的需求。

Mstore 星型寫

控制流方向,SDK 不會頻繁和 RootServer 和 MetaServer 交互,只有在申請新 Chunk 是纔去交互。

數據流方向,SDK 採用併發同步寫三副本的方式,保證數據強一致,架構上更簡單,相比 Raft 等共識協議減少了網絡一跳,降低延遲。

星型寫不支持多點,上層服務需要控制對其數據的多點讀寫請求。

快速切換技術,在星型寫三副本失敗時,不需要馬上修復數據,通過快速重定向到新的三副本使得故障瞬間恢復。

Mstore 一次 IO 技術

爲了減少對磁盤的 IO 佔用,我們對寫請求做了合併,讓多用戶請求轉換成一次磁盤請求。

對磁盤存儲格式的優化設計,使得每次磁盤請求只產生一次 IO,這是性能優於 Ceph 的原因。

用戶請求邊界保存在存儲格式的 Header 結構中,使得異常恢復時能區分請求的邊界,實現寫請求的原子性。

此外存儲格式的 Header 中還保存了數據的 CRC 信息,保證數據的正確性。

Mstore——存儲格式 Header

存儲格式 Header 包含以下字段:

1.prev_size 前一個請求的 size

2.curr_size 當前請求的 size

3.prev_crc 前一個請求的 checksum

4.curr_crc 當前請求的 checksum

5.flags 一些標識位

6.self_cksumHeader 本身的 checksum

Mstore 數據版本

Mstore 存儲的用戶數據是有版本的,根據數據的版本可以實現:版本號遞增,寫請求通過版本保證請求的連續性;讀取數據帶上版本號,保證讀取的副本是新的;數據巡檢服務根據數據版本保證合法的副本。

Mstore 數據讀寫規則

Blob 只能單點寫,通過租約機制做互斥。

Blob 支持多點讀,由用戶負責同步多個節點的版本。

Mstore 可觀測性

Mstore 系統已經擁有完善的監控、告警體系。爲了讓系統能夠以更加白盒的方式在線上運營,我們實現了 Trace 能力,目的是能觀測 Mstore 系統以及其依賴的系統的每次請求各個階段的執行情況。這也有利於後續我們對系統性能做優化。Trace 已經可以對接美團的 Mtrace 平臺。

Mstore 的 Run To Complete 線程模型

爲了最大化降低延遲,我們採用了 Run To Complete(RTC)線程模型,即:一個請求在生存週期內都由一個線程處理。以下爲 ChunkServer 的整體結構。

爲了增加系統併發度,RTC 模型仍然是多線程的。不需要互斥的請求(Req1),在本線程執行完畢。

需要互斥的請求(Req2、Req3、Req4),這些請求由第一個請求所在線程處理。程序保持簡單,模塊從上到下以同步的方式調用。

利用 C++ 的 RAII 技術,在請求析構過程回調執行鏈表下一個請求,將異步動作收斂在一處。

Mstore 的裸盤系統

經過我們對 ChunkServer 的性能測試,發現軟件棧中大部分的耗時來自文件系統操作磁盤,其次是網絡 IO。下圖是我們使用 Trace 系統得到的延遲信息。

基於以上結論,我們研發了用戶態文件系統(裸盤系統),它設計成針對 Blob 特點的磁盤管理方式,簡單、高效。我們在裸盤系統下抽象出 BlockDevice 層,使其能適配不同的設備,如 SPDK、IOuring 等。目前我們使用 SPDK 作爲磁盤驅動,實現 ChunkServer 全棧用戶態。

裸盤系統的元數據包括,SuperBlock 區、BlockTable 區、ChunkTable 區,Padding 區是預留的未使用空間,剩下的是數據區。

SuperBlock 區:裸盤系統的整體信息,磁盤號、是否格式化、Block 數量、Chunk 數量等。

BlockTable 區:記錄系統數據塊的分配情況。

ChunkTable 區:記錄系統 Chunk 的分配情況。

Chunk 在創建時候在 ChunkTable 申請一個存儲區域,記錄 Chunk 的元信息,刪除 Chunk 的時候歸還這塊區域給 ChunkTable。

Chunk 在寫入數據的時候會在 BlockTable 裏面申請一個 Block,刪除 Chunk 的時候會把 Chunk 的所有 Block 歸還給 BlockTable。

Chunk 的 Block 按照寫入的順序以鄰接表的形式保存在 BlockTable 中。

Mstore 的系統延遲

ChunkServer 自身延遲約 26us,其中 spdk 佔用 11us,後續將對 ChunkServer 各個模塊精細優化。

Mstore 的系統吞吐

我們還做了 ChunkServer 的壓力測試對比,同等壓力下,寫吞吐幾乎是 Ext4 文件系統的 2 倍,延遲比 Ext4 低很多;讀吞吐也高於 Ext4,但是因爲 Ext4 有文件系統緩存,所以相比之下 Ext4 的讀平均延遲要低一些。後續我們會看需求在裸盤系統基礎上利用 OptaneSSD 設備實現緩存。

Mstore 測試體系

建設 Mstore 之初我們就考慮系統穩定性的重要,因此我們建設了完善的測試體系。

Mstore 落地情況

EBS 整體架構

EBS 系統(塊存儲)是應用在 MStore 的第一個項目。EBS 有 4 個子系統:BlockMaster、BlockServer、Client、SnapshotServer。

BlockMaster:塊服務的管理節點,維護塊設備的元信息,分配 BlockServer。簡稱 BM。

BlockServer:塊服務的數據處理節點,接收塊設備的所有 IO。簡稱 BS。

Client:塊設備的客戶端。

SnapshotServer:塊服務的快照服務器。簡稱 SS。

業界對標:

EBS 數據組織

一塊盤(Vdisk)被劃分成多個 Segment,典型大小 64G,一個 Segment 由某個 BlockServer 處理。

BlockServer 會將一個 Segment 的所有請求以 Writeaheadlog(WAL)的形式寫到 MStore 的 LogBlob。

每個 Segment 又劃分成多個 Entry,每個 Entry 對應 MStore 的一個 ExtentBlob。

這樣組織數據的好處是:

1、將多個 Entry 的隨機寫轉化成一路順序寫,起到 group commit 的作用。

2、每個 Entry 對應一個 ExtentBlob,這樣多個 Entry 之間沒有聯繫,回刷能並行執行。

3、在讀取的時候如果一個請求跨越幾個 Entry,這幾個 Entry 之間也可以併發的去讀。

EBS 索引

BlockServer 處理請求先將數據寫入 WAL 之後回刷到 Entry 裏面,爲了保證回刷前的數據可讀到,需要在 WAL 之上建立索引。

索引是全內存緩存的,索引結構由 UpdateTable+BaseTable 組成。UpdateTable 是可以讀寫的(Mutable),BaseTable 是隻讀的(Immutable)。

定期做 Checkpoint 有利於系統重啓快速恢復,會生成一個新的 SecondaryUpdateTable,舊的 UpdateTable 變爲只讀,和原來的 BaseTable 合併生成一個新的 BaseTable。

這麼設計索引的好處是,BlockServer 的操作都針對只讀的 BaseTable 操作,簡化程序處理,減少操作 BaseTable 的鎖競爭,有利於性能。

EBS 回刷 WAL

BlockServer 會定期把 WAL 的數據回刷到 Entry 裏面,按照 LogBlob 從頭到尾順序回刷。實現過程要注意幾個時間點,才能保證各子系統能正確工作:

1、最舊的 Log 點、2、Dump 的起始點、3、Dump 的結束點、4、索引 Checkpoint 點、5、最新 Log 點。時間順序:1<=2<=3<=4<=5。

Log 回收區:【最舊的 Log 點,Dump 的起始點),這個區間的 Log 可以隨時被回收掉。

Dump 數據區:【Dump 的起始點,Dump 的結束點),這個區間是 Dump 操作正在作用的區間。

索引 BaseTable 表示的區間:【最舊的 Log 點,Checkpoint 點),這個區間表示 Checkpoint 點之前的所有數據的索引,涉及 WAL+Entry。

索引 UpdateTable 表示的區間:【Checkpoint 點,最新 Log 點),這個區間表示 Checkpoint 點之後的所有數據的索引,只涉及 WAL。

|嘉賓介紹|

楊立明

美團存儲技術中心技術專家

專注於 kv 存儲、數據庫、存儲等領域的研發工作,曾就職於京東、百度、頭條等互聯網公司。於 2020 年加入美團,致力於美團新一代統一存儲 MStore 的建設工作。

本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源https://mp.weixin.qq.com/s/lwwLd0CoR9Hkzj1Bj5GD3A