1. 前言
分布式文件存儲系統其作用主要有兩個:其一存儲海量的文檔、圖片、視頻等blob類數據,其二作為分布式表格系統的持久化層,如 HDFS於HBase。流行的分布式文件存儲系統有很多,如google的GFS、及其開源的實現版本HDFS和Facebook的Haystack等等。既然是分布式,肯定有多個機器甚至機房參與了,機器之間通過網絡互連溝通;而又只要存在着溝通,由於昂貴的溝通成本(CAP理論)導致其實現原理會變得復雜。
其實站在用戶的角度思考:其需求功能非常簡單,能成功快速增刪讀寫文件就ok了,如同操作本地的單機文件系統一樣簡單。例如如下:
a. 讀取文件操作,read函數: ssize_t read(int fd, void* buf, size_t count);
b. 寫入文件操作,write函數: ssize_t write(int fd, const void* buf, size_t count)。
2. 問題
既然分布式文件系統是由許多數據節點組成的集群,如果你是一個操心的主,可能會進一步的思考,其實現背后的諸多問題:
2.1. 寫文件操作
a. 在單機本地文件系統,我們不用關心數據存放的節點,因為默認寫本地服務上;那在分布式文件系統上,文件寫到哪個節點上或者哪些節點上了呢(數據副本策略)?
b. 這些數據節點怎么從集群種選置和敲定的(數據放置策略)?
c. 客戶端直接和這些數據節點同時溝通,還是只是和其中的一個數據節點代表做溝通呢(數據復制策略)?
d. 另外,數據寫入成功與否直接影響服務的可靠性,所以寫入操作的成功或失敗結果返回非常重要。那么在分布式文件系統里,寫入的成功如何來度量?是成功地寫入到一個數據節點,還是成功地寫入到多個數據節點后算操作成功,然后返回結果給客戶端呢(數據復制時同步異步策略)?
2.2. 讀取文件操作
同樣的,客戶端在讀取數據文件時,又到哪個數據節點上去取數據呢(數據節點選擇策略)。
2.3. 數據組織與索引
在單機本地文件系統里,由於linux的io機制,文件名與物理磁盤的block編號自然建立了一一映射的關系。然而在分布式文件系統里,由於多了數據節點的維度,終端訪問的文件名與其所在的集群物理磁盤block位置之間的索引關系會是什么樣的?文件的邏輯結構如何組織的?
2.4. 空閑時段和心跳時期
在高峰期,集群服務在頻繁地與客戶端發生的溝通和任務調度執行;我們知道服務集群是7*24不休息的,那么在半夜等空閑的低負載時期,集群服務又會“偷偷摸摸”干些啥事情呢?
當集群規模逐漸擴大時,節點不可用、網絡異常、磁盤損壞等各類的故障發生率高:假設一個節點每天的故障發生率是1%,那么由一個100節點組成的集群每天的故障發生率變成了0.64(1-0.99^100)。因此集群服務的健壯容錯、數據可用性也是分布式文件系統的重要衡量指標之一。那么一旦故障發生,服務必須仍能正常提供工作,並且具有能及時的檢查並進行數據的遷移與修復能力。而集群服務通過心跳機制完成各個節點間的負載或死活狀態的信息共享與故障檢測;通過節點鏡像、數據遷移操作來修復數據節點故障或數據不均衡的現象。
以上僅是關於分布式文件存儲系統的一些我個人的思考,有所不對或片面不全的地方,后續再補充吧。
參考:
1. 《大規模分布式存儲系統:原理解析與架構實戰》楊傳輝著
2. 《大數據日知錄》張俊林著