海量小文件存儲最優解決方案,杉巖數據MOS完美解決

面對千億量級的小文件,存儲系統壓力山大

所謂小文件,指的是存儲佔用空間相對較小的文件,一般來說低於64MB的文件就可以被認定爲小文件,而大量的小文件大小則在幾KB到幾十KB之間。在雲計算、大數據業務中,文本、圖片、音樂等是典型的小文件應用場景。

隨着數字化創新的加速,組織內部的數據呈現出指數級增長的趨勢,特別是小文件更是隨着業務增長到一個巨大的量級。與大文件的存儲不同的是,大量磁盤在小文件存儲場景中的性能極低,單塊企業級SATA磁盤如果全部存儲4KB左右的小文件,帶寬只有520KB/s,遠遠小於應有的120MB/s的帶寬標準值,很容易因爲存儲系統的性能不足造成上層應用“卡頓”。把磁盤全部換成固態盤固然可以解決問題,但是,固態盤的價格數倍於SATA磁盤,對於很多用戶來說,全面的應用固態盤在成本上仍然不現實。

百億~萬億量級的小文件對存儲性能提出

而且,每個應用場景對於存儲系統的性能往往有着不同的要求。例如,某領先電商平臺已經存儲了數量以百億計算的圖片文件,這些圖片平均大小在15KB左右,用戶對於這些圖片文件的讀取完全是隨機讀取,一旦大量用戶同時在線訪問網址或者搜索商品,往往就會給存儲系統的隨機讀寫能力帶來巨大的挑戰;在交警系統中,路口的抓拍攝像頭會將違章圖片傳送至區中心的計算服務器,不僅攝像頭數量多,而且每臺攝像頭每天都可能生成數千乃至上萬張照片,某市每天相關圖片寫入甚至超過一億張,要降低存儲系統的壓力,就需要及時刪除正常的圖片,這對存儲系統的寫入、刪除能力要求很高。

海量小文件存儲最優解決方案,杉巖數據MOS完美解決

海量小文件帶來的問題

1、海量數據的性能問題。這是64K寫的性能測試,一開始的1萬到4億個對象,這個時候會發現寫入的性能逐步下降,從開始有15K的oes到下降到2.5,實際上下滑比例已經達到了80%多,海量小文件的衝擊是非常大的。

究其原因,如果用的是Fd,底下的文件是要從Fd到dentry再到inode,superblock,1億的文件,256B,它已經佔了24G,小文件帶來的是要直接操作磁盤,直接操作磁盤會導致性能下降,海量的小文件會破壞空間的連續性,會產生大量的隨即讀寫。海量小文件會有大量源數據,性能還是不能得到流暢。

2、數據恢復效率問題, 數據在做恢復的過程中效率的問題,海量場景下恢復的速度,後者是前者的10倍,海量的小文件場景下,數據恢復的速度比較緩慢,而且效率很低,在此期間如果剛好不巧有業務請求過來,有可能會看到Slow Requses或是blocked,是存在風險的。

3、擴容、恢復以後集羣的性能還會出現驟降的情況。如果做了擴容或是故障恢復,這個時候大量的小文件可能會被刪除,可能會出現大量的碎片,這個碎片可能出現在磁盤上,如果不進行碎片的回收,裏面系統的性能會出現驟降的情況,這是我們測的一組數據,前面很平穩,一旦擴容等恢復以後,這個比例會變大。

4、海量小文件的場景,數據的遷移效率比較低。可能想用數據冷熱分層的方式把熱數據移到冷的存儲池,這個時候有大量的小文件在這個過程中會產生遷移,而且這個遷移的過程中前面也會有,遷移以後數據可能進行大量的刪除操作。之前測試的4000萬的小文件遷移消耗時間大於72個小時,算下來要兩天多的時間。這種情況下遷移的效率太低了。

解決小文件問題的幾點想法

海量小文件,是不是可以做合併?合併之後的文件,不是體積很小的文件,空間的使用效率是比較高的,對磁盤還是比較友好的。合併以後是不是可以提高讀寫的性能?

我們都知道,現在流數據,而且是寫在對象裏,源數據是不是可以獨立?爲什麼做獨立?源數據獨立有兩個好處,源數據可以更加靈活的做選擇存儲,可以對這些源數據做一些其他的操作,比如說源數據是不是可以做其他方面的管理、檢索,都很方便的做。是不是可以把源數據部分抽出來?

同步和刪除的流程是不是可以改進?如果做到第一點,文件做了合併的話,傳輸也是可以做合併的,而且刪除操作的時候,批量刪除是可以提升效率的。

基於這三點,Sandstone Mos針對海量小文件的問題提出了方案。

Sandstone Mos海量小文件的方案

第一步我們把源數據從Data pool抽出來進行分離,源數據存在index pool,部署方式是不是和其他的部署方式不一樣,沒必要和Data pool綁在一起。每個對象把源數據抽出來以後,放在BI,源數據有它的BI,會有對應的Data pool數據實體。我們去到ID裏的Index,多個對象放在一起管理,這個時候很方便的能實現多個版本的數據管理。

這方面我們也需要一些數據,簡化整體的數據結構。比如說讀寫數據有非常重要的結構,在應用數據結構的時候發現有很多數據,這些數據不好的地方是沒怎麼用、沒什麼用,放在這裏很佔空間。裏面有RGW很佔空間,讀寫數據的時候其實沒必要關心這個對象是什麼樣的,我們也去掉一部分的冗餘數據簡化數據結構。

在這上面我們也做了文件合併的工作。開始的想法是不同的對象可以寫到一個大項裏,實際上這裏會有幾個問題,對象寫進來以後應該朝哪個地方寫?後面會講一下大概的流程,處理小文件寫入的時候可不可以給一些因素簡化流程?不同的bucke的小文件合併到不同的大文件裏,如果對象是同一個bucket會寫到同一個大對象裏。我們都知道用的是shard的思想,BI分了不同的shard,爲了簡化處理流程,,不同bucket的小文件存到不同的大文件。

文件合併以後要讀的時候應該怎麼讀?小文件的讀取比較簡單,存進去改一下加上offs和lenght就可以了,所有的對象指向的數據實體只有一個,對象讀的時候知道開始位置就可以得到對應小文件的數據。還是會有問題,簡單的話是合併就完了,問題是這個東西進來以後,應該寫到哪個對象上?所以對象進來以後可能好幾層,這裏就會有一個問題,假設兩個對象是寫到同一個大對象上,這個大對象的空間分配會是一個關鍵的問題,對象的空間分配一定要統一一個來源,可以避免寫同一個對象,保證區間不會相互交集。我們在Bucket使用omap_key存儲大對象元數據,可以起到空間分配的作用,對象寫進來以後,最後是不是要確定對象放在哪個Bucket shard上,可以看到需要用哪個merged object,可能第一個寫0到24,第二個會記一個狀態,會把他的狀態記爲已經使用,下一次線程過來就不會用空間。會把空閒的空間分配給他,我每個線程寫的時候拿到的空間分配信息之後,就可以寫相應的偏移。我們每個對象在上面都做了空間的管理。

刪除操作可能會出現幾個問題,刪除的空間怎麼進行回收?可能刪了幾個小對象後大對象整體會出現空洞的情況,什麼時候進行整體的回收?進行整體回收的時候這些小文件要怎麼進行適度的遷移?前面說的空間管理情況下有條目的狀態,既可以在空間分配中用到,也可以在刪除小文件的時候用到,刪除小文件的時候是異步刪除的方式,可以在這個大對象上做個狀態的更改,裏面會涉及到兩個操作,不單只是刪除小文件的時候要刪原來的小文件BI,還要改大BI的狀態。

我們有兩個對象可能被刪除會標deleted的狀態,刪除的時候如果數據不進行立刻的回收,空間是存在一定的浪費。這個時候要靈活運用object的接口,這個時候空間做了一定的回收,所以這個接口是比較友好的,對於快速釋放空間,提高空間的利用率,有可能大對象的區間被刪除,當空間使用率達到一定程度的時候,我們要進行整體的回收,大對象可以反向索引到每個小對象上,小對象也需要記錄自己所處的大對象,這兩個操作是爲了後面鋪墊的,要做刪除操作的時候,小對象必須自己清楚,我是屬於哪個大對象的?刪除的時候可以在上面記這個狀態,大對象有要記自己被哪些小對象引用,爲什麼這樣處理?如果說空間使用率低到一定程度的時候,要進行整體的回收,這個時候還在使用小文件怎麼辦?大對象必須反向索引到有哪些小對象在用它?這個時候我們把小文件的數據挪出來,遷移到其他大對象裏。整體的機器操作是完全的異步方式,如果你在刪除對象的時候會進行res的,爲了處理其他的問題,把整個過程變成異步的,包括BI的刪除和數據的刪除都變成異步的方式。

同步和數據遷移原理是一樣的,無非是把大量的數據從一個站點,從一個存儲池遷到另一個存儲池,這一點是最爲頭疼的,會涉及到非常多邏輯的問題,比如說合並後的文件是怎麼進行同步的?小文件的元數據,合併以後的文件進行同步,元數據怎麼同步,是不是會存在先後順序的問題?

大家如果瞭解的話,多站點的同步分爲兩部分,一個是全量同步,一個是增量同步,兩個同步的方式和base的實際結構是不太一樣的。如果你是全量投入的情況下,AB兩個站點是進行全量同步的,我做全量同步的時候會把裏面的對象都拿過來,增量同步就不一樣。先分場景做,我第一步是先把這些合併之後的文件、數據整體的拉過去,包括前面提到的大對象,實際上也有自己的BI,這個時候對我來說也是一個對象,我會把這些數據統一丟過去,小文件的元數據還是維持。

增量同步的情況比較複雜,這個大對象是寫到100,這個時候怎麼把它同步過來?這裏面有點取巧,像這種情況下,我們要處理這個邏輯,前面全量可能把這個拉過去,根據多個BI,如果發現是多條邊、是寫在同一個同類項上,這個時候會把數據做合併類似於前面同步的方式,把數據合併丟過去。最後源數據還是通過BI的方式,把源數據拉過來,每次請求的效率會比以前高一些。

兩個數據池遷移的時候,跟全量同步的場景是一樣的,全量同步的情況下和存儲數據池的遷移是一樣的場景,這個時候沒有單列存儲池的場景。

總結

1.海量小文件的性能。我們在做完文件合併以後,文件數是能明顯下降的,解決海量數據場景下的性能問題,文件合併以後,對於磁盤來說是比較友好的,合併以後可能是比較大的文件,比如說我們合併至少都是4M的文件,合併以後文件的數據量會明顯下降。

2.恢復效率。文件合併以後效率也可以得到巨大的支撐,原來都是32K的文件,有100個32K的文件,合併以後是3M多的文件,每次請求要恢復的文件數目明顯減少了。

3.擴容後的性能驟降的問題,合併後的文件對於空間的使用率更高,就算會出現大量的數據刪除情況,這個時候對於磁盤的使用也是更加友好的,因爲這個時候磁盤也不會出現過度的空洞碎片。

4.數據遷移的整體做了優化,數據合併之後遷移的效率也會明顯的提高,前面可能分了100個小文件,可能是請求100次的32K文件,可能是100次32K的請求,合併之後只需要一次移過量就可以了,後面的所有操作都是不需要再跨兩個Pool。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章