雲端計算(十一)- HDFS快照(HDFS Snapshots)
HDFS快照是一個只讀的基於時間點檔案系統拷貝。快照可以是整個檔案系統的也可以是一部分。常用來作為資料備份,防止使用者錯誤和容災。
HDFS實現了:
- Snapshot 建立的時間 複雜度為O(1),但是不包括INode 的尋找時間
- 只有當修改SnapShot時,才會有額外的記憶體佔用,記憶體使用量為O(M),M 為修改的檔案或者目錄數
- 在datanode 上面的blocks 不會複製,做Snapshot 的檔案是紀錄了block的列表和檔案的大小,但是沒有資料的複製
- Snapshot 並不會影響HDFS 的正常操作:修改會按照時間的反序記錄,這樣可以直接讀取到最新的資料。快照資料是當前資料減去修改的部分計算出來的。
可以被快照的目錄
快照會儲存在snapshottable的目錄下。snapshottable下儲存的snapshots 最多為65535個。沒有限制snapshottable目錄的數量。管理員可以設定任何的目錄成為snapshottable。如果snapshottable裡面存著快照,那麼資料夾不能刪除或者改名。
網路的snapshottable目錄現在是不允許的。另外如果一個目錄的父目錄或者子目錄是snapshottable,那麼這個資料夾不能作為snapshottable。
快照的目錄
對於一個snapshottable資料夾,".snapshot" 被用於進入他的快照/foo 是一個
/foo/.snapshot/s0/bar引用快照副本/foo/bar。常用的API和CLI能夠在".snapshot" 的路徑下執行。下面是一些例子。 列出snapshottable目錄的所有快照
-
hdfs dfs -ls /foo/.snapshot
-
hdfs dfs -ls /foo/.snapshot/s0
-
hdfs dfs -cp /foo/.snapshot/s0/bar /tmp
注意 ".snapshot"這個名字已經被HDFS保留使用者不能建立這個同名目錄。如果".snapshot"正在被前一個版本的HDFS使用,他必須在升級之前重新命名,否則會升級失敗。
操作
管理員操作
本節的操作需要超級使用者許可權。
快照可用
快照目錄建立。如果這個操作成果,那麼目錄會變成snapshottable。
命令
-
hdfs dfsadmin -allowSnapshot <path>
- 引數:
path snapshottable目錄路徑.
同時請參考在HdfsAdmin中 void allowSnapshot(Path path)的API。
快照不可用
資料夾裡面的所有快照在失效快照前必須被刪除,如果沒有該目錄會被建立。
命令:
-
hdfs dfsadmin -disallowSnapshot <path>
- 引數:
path snapshottable目錄路徑.
同時請參考在HdfsAdmin中void disallowSnapshot(Path path)的API。
使用者操作
本小節描述使用者操作。注意HDFS超級使用者可以執行所有的操作除了有許可權的需求的操作。
建立快照
snapshottable目錄建立一個快照。這個操作需要snapshottable目錄的許可權。
命令
-
hdfs dfs -createSnapshot <path> [<snapshotName>]
- 引數:
path The path of the snapshottable directory. snapshotName 快照名字。如果沒有指定,會用時間戳生成一個預設的名字格式是"'s'yyyyMMdd-HHmmss.SSS", 例如 "s20130412-151029.033".
可以createSnapshot(Path path)和createSnapshot(Path path, String snapshotName)在檔案系統中的API,方法的返回值是snapshot 路徑
刪除快照
從一個snapshottable目錄刪除的快照。這個操作需要snapshottable目錄的許可權。
命令:
-
hdfs dfs -deleteSnapshot <path> <snapshotName>
- 引數:
path The path of the snapshottable directory. snapshotName 快照名字
參考void deleteSnapshot(Path path, String snapshotName)的API
重新命名快照
重新命名快照。這個命令也需要snapshottable目錄的許可權。
命令:
-
hdfs dfs -renameSnapshot <path> <oldName> <newName>
- 引數:
path The path of the snapshottable directory. oldName 老的快照名字 newName 新的快照名字
參考void
renameSnapshot(Path path, String oldName, String newName)的API
得到snapshottable目錄列表
獲取當前使用者的所有snapshottable。命令:
-
hdfs lsSnapshottableDir
- 引數: 無
參考SnapshottableDirectoryStatus[]
getSnapshottableDirectoryListing()的API
獲取快照差異報告
得到兩個快照之間的不同。需要兩個目錄的許可權。
命令:
-
hdfs snapshotDiff <path> <fromSnapshot> <toSnapshot>
- 引數:
path The path of the snapshottable directory. fromSnapshot 開始的快照名字 toSnapshot 結束的快照名字。
參考SnapshotDiffReport getSnapshotDiffReport(Path path, String fromSnapshot, String toSnapshot)的API