趙二狗剛剛畢業,應聘進入了錘鈕匹科技有限公司,成為了這裡的新員工。入司的第一天是分配宿舍(背景音:天哪,還有宿舍!羨慕嫉妒恨!)。跟他在同一個宿舍的是公司的老員工王大拿,王大拿是該公司的架構師,對公司的情況基本上無所不知。請注意,這裡說的是公司的八卦新聞,哈哈! 趙二狗進了宿舍,王大拿正在那裡噼裏啪啦的敲鍵盤... ...

趙二狗: 前輩,我是新報道的同事。

沒有任何反應。

「前輩」,趙二狗提高了嗓門。

還是沒有任何反應。

「前輩!」,趙二狗大喝一聲。

王大拿忽的從椅子上站了起來,「幹毛,嚇死老子了」,王大拿略帶怒氣的說。

「前輩,我是新入職的同事,跟您一個宿舍,認識您很高興!」,趙二狗面帶笑容的說。

一聽這樣,王大拿笑了,「好說,好說,你隨便坐吧,我這忙著調程序呢」。

「週末還不休息!?」趙二狗小聲嘀咕著。

王大拿很憤憤,「是啊,孃的,遇到個Bug,阻塞好幾天了。」

「什麼問題?」趙二狗問。

「說了你也不懂,小鮮肉」,王大拿不屑的說。

王大拿繼續說, 「你知道什麼是快照嗎?」

「切,不就是快照,那有什麼不懂的,我也是堂堂985的碩士研究生,之前專門搞存儲的」,趙二狗很不爽。

「好小子,那你講講」,王大拿突然提起了興趣。

於是趙二狗同學開始娓娓道來... ...

什麼是快照

快照是存儲系統中的一種數據保護技術,主要是實現數據的邏輯保護。所謂邏輯保護,就是當數據出現誤刪除或者病毒等原因導致數據破壞的情況。通過快照技術,可以將數據恢復到某一個時間點的數據。

「不錯,接著說」,王大拿覺得趙同學還有兩下子。

從名字上可以猜出來,快照就好像給數據拍了一個照片,就好像我們日常生活中給人拍照片類似。以生活中拍照片為例,比如給你家娃娃拍了他2歲的照片,等他到5歲的時候,樣子變化很大。這個時候你想看看他2歲的時候長什麼樣,那你就可以拿出他2歲的照片看看。

對於存儲中的快照技術也是類似,在某個時間點,你給某個磁碟(或者存儲中的LUN)打一個快照,相當於讓存儲系統給這個磁碟拍了一個照片。當之後的使用過程中發生了意外,比如病毒把數據搞壞了等等。這個時候你就可以通過快照知道原來的數據是什麼樣的,這樣數據就可以找回來了。

快照的實現原理

」不錯,不錯,那快照的實現原理是什麼呢?「,王大拿覺得有點小看小趙同學了,於是接著問。

快照可以在文件系統或者塊設備層面實現,我們以塊存儲為例。塊存儲從普通用戶的角度來看就是磁碟。從用戶的角度磁碟其實就是一個線性空間,可以理解為一個很大的數組,比如512G或者4TB等。但磁碟的讀寫最小單位是一個扇區,也就是512位元組。這樣可以不用關心,這個跟我們後面講的快照的原理也沒有太大關係。

有了磁碟的這個概念,那麼快照就比計較容易理解了。對於存儲系統而言,磁碟實際上是從存儲池劃分的一塊空間而已(這一點與我們普通PC的事物磁碟有所不同),如圖2所示,假設原始磁碟在存儲池中有如圖的一塊空間,而磁碟在存儲系統中其實就是一個數據結構而已,只不過這個數據結構描述了磁碟在存儲池中的空間範圍。

磁碟是一個數據結構,快照實際上也是一個數據結構。對磁碟做快照,其實就是在存儲系統中創建一個數據結構,讓其描述的數據範圍指向原始磁碟指向的存儲池的範圍即可。這樣快照的數據就和磁碟的數據一模一樣,具體可以參考圖2 A進行理解。 但是原始磁碟的數據是會變化的,也就是會被重新寫新數據的。這個時候怎麼保證快照的數據還是打快照那個時間點的數據呢?問題的關鍵就在磁碟對數據的描述和管理。在存儲系統中,將磁碟劃分為固定大小的塊(比如4KB),然後通過某種機制(比如點陣圖)對這些磁碟塊進行管理和標記。當有應用對磁碟寫新的數據的時候,磁碟管理軟體就會將原始數據拷貝到新的地方,然後讓快照的指向改為這個新地址,而磁碟原來的地方就可以將數據寫入。這樣對於磁碟而言,數據發生了變化;而對於快照而言,快照的數據還是打快照那個時間點的數據。 「嗯,懂得很多嘛,小趙」,王大拿似乎很滿意趙二狗同學的答案。「問題是這種方式需要在底層複製數據,會影響原始磁碟的性能」。

快照的2種實現

是的,目前快照有2中實現方式,一種是我上面介紹的方式,稱為COW,全稱為Copy-On-Write。也就是在原始磁碟寫數據的時候會將原始數據拷貝到新的地方。當然,並不是每次寫數據都會拷貝,而是第一次寫數據的時候才會拷貝。這裡有一個點陣圖記錄著已經拷貝過的數據,如果已經拷貝過,則下次再寫數據的時候將不會再拷貝了。 另外一種實現方式成為ROW,全稱為Redirect-On-Write,也就是寫時重定向。這種實現方式的基本原理是當原始磁碟寫數據的時候並不在原始位置寫入數據,而是分配一個新的位置。這種情況下就需要維護磁碟邏輯地址與實際數據位置的對應關係。如圖3是ROW的原理示意圖。

快照的用途與侷限

「你剛才說的快照可以防止數據被病毒破壞,還有其它應用場景嗎?」,王大拿問。 「很多啊」, 趙二狗接著說。 「比如在資料庫應用領域,使用關係型資料庫的業務通常是關鍵業務。因此,需要保證資料庫在出現數據損壞或者丟失的情況下能夠恢復到某個時間點。這樣,通過快照,比如每個小時打一個快照,這樣即使出現問題,最多丟失1個小時的數據,從而保證數據的安全。」

「資料庫為了提升性能可能會同時使用好幾個磁碟,比如Oracle資料庫會用不同的磁碟存放不同的數據。比如數據文件會單獨放在一個磁碟,Redo日誌又會放在另外一個磁碟。並且,Oracle資料庫會校驗兩者的一致性,任何差異可能會導致整個資料庫的不一致,這個怎麼解決?」,王大拿問。 趙二狗回答:「這種情況下就需要一種稱為「一致性組」的技術了,「一致性組」相當於將磁碟打包成為一組磁碟,做快照的時候可以保證這一組磁碟的數據是在同一個時間點的。」

王大拿若有所思:「嗯嗯,但是還有一點,如果我們做了快照,在恢復的時候資料庫是否可以直接恢復?」 趙二狗:「應該可以的啊,因為數據我們都保護了,數據恢復到該時間點後,資料庫可以直接啟動。」 「不一定」,王大拿繼續說「我們舉個例子,資料庫通常是要保證事務性的,為了保證數據的事務性,資料庫對於一個寫數據通常不是簡單的寫,而是要寫一大堆各種日誌,因此對於一個寫數據操作,到我們存儲系統就會變成很多個IO。」 「在我們存儲層面我們是不知道那些IO是某一個事務的,而我們做快照是以IO為粒度進行的。換而言之,也就是我們做了一個快照,可能對於資料庫而言正在處於中間過程。這樣的話,當我們恢復到這個時間點的時候,資料庫並不能直接啟動,而是處於一種數據不一致的狀態,需要手動做恢復處理。」

趙二狗露出了驚訝的表情: 「大拿就是大拿, 那怎麼辦?」 「涼拌,這個沒招啊,臣妾做不到」,王大拿說。

「應用層面上的問題只能在應用層面上解決了,存儲系統本身處於下層,無法感知應用的差異。Oracle層面本身也有數據保護的機制,比如數據備份,或者RAC等。好了,時間不早了,喫飯去吧。」 「好的,大拿,今天我請客,學到不少新東西。」


推薦閱讀:
相關文章