6.824分佈式系統[2]-GFS案例學習

準備工作

閱讀:GFS論文

背景

  • GFS是Google在2003年發出的經典論文,其作爲分佈式文件系統,實際應用在Google的MapReduce框架實現中,作爲原始數據和最終結果存儲的基礎服務。

  • 爲其他上層基礎系統比如BigTable提供服務,Hadoop中的HDFS就是其開源實現。

  • 這篇文章討論了諸如一致性、容錯、網絡性能等分佈式系統工程中的經典問題,啓發了後續很多分佈式文件系統的發展。

爲什麼閱讀GFS的論文

  • GFS使用了map/reduce的架構

  • 好的性能 & 良好的並行I/O性能

  • 其是一篇好的系統論文:從apps到網絡都有細節說明

  • 包含分佈式的許多概念:performance, fault-tolerance, consistency

  • 使用廣泛(Bigtable、Spanner、Hadoop)

一致性是什麼

  • 一致性是保證分佈式系統正確的條件。在有多個副本,並且併發下變得尤其困難。

  • 一致性是分佈式系統中最關鍵的問題,基本所有分佈式系統都必須討論這個問題。

  • 考慮如果在一個程序中寫,但是在另一個程序的副本中讀取的情況。

    • 強的一致性會保證在另一個程序中讀取到的一定是發生在最後一次寫入之後。

    • 弱的一致性無法對其進行保證,可能會讀取到過時的數據。


  • 強一致性可以保證讀到最新的寫信息,但是對性能肯定會造成影響,好的系統設計就是在這兩點中進行平衡。

理想的一致性模型

分佈式文件系統需要達成的“理想的“一致性就是多節點上面操作文件表現處理單機跟本地文件系統一樣。

  • 如果兩個應用程序同時寫入同一文件怎麼辦?

    • 在單機,數據常常有一些混合的內容。即兩個程序的處理可能是交錯的。


  • 如果兩個應用程序同時寫入同一目錄怎麼辦

    • 在單機,使用了鎖。一個應用程序處理完畢後,再處理第二個。


  • 挑戰

    • 多磁盤

    • 機器故障,操作無法完成。

    • 網絡分區,可能不能夠到達所有的機器和磁盤。


  • 挑戰難以解決的原因

    • 需要客戶端和服務器之間的通信

    • 協議可能會變得複雜


不同的模型一致性考慮不同的權衡

+ 可串行性(serializability)
+ 順序一致性(sequential consistency)
+ 線性一致性(linearizability)
+ 單項一致性模型(entry consistency)
+ 鬆散一致性(release consistency)

GFS的目標

  • GFS中節點失效就是常見的(每天1000臺機器中大約3臺失效)

  • 高性能:大量

  • 有效的使用網絡

設計

  • master存儲(directories, files, names)

  • 存儲64MB的塊,每個塊就作爲一個linux文件。

  • 每個塊在三臺服務器上面做備份(保證可用性,負載均衡)

  • 塊爲什麼這麼大(攤銷間接費用、減少master中的狀態大小)

  • master掌握目錄的層次結構

    • 文件夾中有哪些文件

    • 對於文件,維護信息:哪些節點存儲了此文件。

    • master在內存中維護狀態(每個塊的64字節元數據)

    • 主數據庫具有用於元數據的私有、可恢復數據庫

      • 操作日誌刷新到磁盤

      • 檢查點

      • master快速恢復


    • shadow masters略微落後於master


客戶端讀

  • 發送文件名和塊索引給master

  • master回覆具有該塊的服務器集

    • 回覆版本號

    • client緩存信息


  • 請求塊服務器

    • 版本號(如果版本號錯誤,重新連接master)


primary

primary是一個副本節點中比較高級的節點。

修改現有文件

  • client請求master 塊的位置 和primary的位置

  • master回覆塊服務器,版本以及primary的位置

  • client根據網絡拓撲計算副本鏈

  • 客戶端將數據發送到第一個副本節點,然後此副本節點轉發給其他人

  • 副本節點會ack,表明數據已被接收

  • client 告訴primary寫入數據

  • primary分配序列號並寫入

    • primary 告訴其他副本寫入

    • 全部成功後,回覆client


  • 如果另一個客戶端併發在同一位置寫入數據,該怎麼辦?

    • c1 與c2 可能會交替的寫入,結果是一致性的,但是不能保證的。


添加文件

  • client 請求master 塊的位置。

  • client將數據發送給副本,但是沒有指定偏移量。

  • 當數據在所有的塊服務器上後,client聯繫primary

  • primary分配序列號

  • primary檢查是否能夠剛好添加到一個塊中

  • primary爲添加選擇偏移量,進行添加

  • 轉發請求到其他副本

  • 失敗後進行重試

    • 不能使用下一個可用偏移量,因爲在失敗的節點中可能會有空字節。


  • GFS支持原子操作,保證至少一次添加,主Chunk服務器選擇記錄需要添加到的文件位置,然後發送給其他副本。

  • 如果和一個副本的聯繫失敗,那麼主Chunk服務器會告訴客戶端重試,如果重試成功,有些副本會出現追加兩次的情況(因爲這個副本追加成功兩次)。

  • 當GFS要去填塞chunk的邊緣時,如果追加操作跨越chunk的邊緣,那麼文件也可能存在空洞。

失敗情況

塊服務器的失敗會引起client重試。
master失敗會導致GFS不可用,shadow master會服務只讀的狀態。可能會返回過時的數據。

總結

性能,容錯,一致性(performance, fault-tolerance, consistency)的案例研究

  • 優勢

    • 大量的順序讀取和寫入

    • 追加文件高效

    • 大的吞吐量

    • 數據容錯(3個副本)


  • 劣勢

    • master服務器的容錯

    • 小文件(master服務器的瓶頸)

    • client會看到過時的數據(弱的一致性)

    • 追加可能重複


GFS案例問答

爲什麼添加數據執行至少一次"at-least-once"語義,而不是精準的一次?

實現困難,primary需要保留重複的狀態。狀態必須在服務器之間複製,以便如果primary出現故障, 此信息不會丟失。

應用程序如何知道塊的哪些是有數據的塊,哪些是重複的數據

可以在有效記錄的開頭做標識(magic number)就可以知道有數據的塊。
檢測重複的塊可以爲每個記錄都有一個特殊的UID標識。

論文中提到的reference counts是什麼意思

  • 他們是實現快照copy-on-write(寫時複製)的一部分。

  • 當GFS創建快照時,它不復制塊,而是增加每個塊的引用計數器。這使得創建快照的成本不高。 如果客戶端寫入了一個塊,並且主服務器注意到引用計數大於1,此時,主服務器會首先創建一個副本,以便客戶端可以更新副本(而不是快照的一部分)。

參考資料


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