假設有n臺服務器,
計算這n臺服務器的IP地址的哈希值,
把這些哈希值從小到大按順時針排列組成一個「服務器節點環」,
客戶端須要存儲一系列的「鍵值對」到這些服務器上去,
計算這些「鍵」的哈希值,
看看這些「鍵」的哈希值落在「服務器環」的哪些區間,
以下圖所示:
根據上圖示意,數據將被存儲在「順時針方向上的下一個服務器節點」
讀取數據時,也是先根據「鍵」的哈希值,找到這個服務器節點,
再向這個節點索取數據。
2.數據如何均勻的分佈?(虛擬服務器)
假設服務器數量較少,
極可能形成有些服務器存儲的數據較多、承擔的壓力較大,
有些服務器就比較空閒。
這時就要把一臺服務器虛擬化成多臺服務器,
具體的操做辦法:
在計算服務器對應的哈希值時
能夠在IP地址字符串加多個「尾綴」
好比:
10.0.0.1#1
10.0.0.1#2
10.0.0.1#3
....
這樣,一臺物理服務器就被虛擬化成多臺服務器,
對應「服務器環」上的多個節點。
3.如何實現數據的熱備份?
以順時針方向看「服務器環」
當有客戶端把數據存儲在第1臺服務器上後,
第1臺服務器負責把該數據拷貝一份給第2臺服務器
以此類推,
也就是說「服務器環」上的每個節點,都是上一個節點的熱備份節點
同時,一個服務器上存了兩類數據,一類是自身的業務數據,一類是上一節點的熱備數據。
注意:這裏所說的服務器,都是物理服務器,不是虛擬服務器。
以下圖所示
4.如何讓客戶端發現全部服務端?
每一個服務器節點都要維護一個對照表
這個對照表中包含全部服務器,(IP地址和IP地址的哈希值對照表)
配置客戶端時,只要讓客戶端知道任意一個服務器的IP地址便可
客戶端能夠經過獲取這個服務器的對照表從而知道全部的服務器
客戶端初始化的時候,這個對照表也存儲在客戶端一份
客戶端根據這個對照表來存取數據
注意:這個對照表是有一個版本號的,具體的用途見下面的描述
5.如何應對服務器異常?
假設數據在節點1上讀寫不成功,
咱們就認爲這個節點存在異常,要把它從服務器羣集中拿掉。
客戶端先在節點2(節點1的熱備節點)上完成相應的讀寫工做,這時客戶端就能夠去作其餘工做了。
而後節點2向節點0索取數據(這些數據是本應該備份在節點1上的數據)
而後節點2向節點3推送數據(這些數據是節點1上的數據,如今要備份在節點3上)
而後節點2更新其對照表,把節點1從其對照表中移除,並更新對照表的版本號
當有任何客戶端與節點2交互的時候,
就會發現節點2上的對照表的版本號比本身持有的對照表要高
此時,客戶端就更新本身的對照表
這些客戶端再與其餘服務器交互的時候
其餘服務器發現客戶端攜帶的對照表版本號比本身持有的要高
此時,其餘服務器更新本身的對照表
注意:這是一個「發散式的連鎖反應」,不會影響生產。
還可讓節點2告知節點3須要更新對照表
當節點3更新完以後,再讓節點3告知節點4....
以此引起「環式的連鎖反應」
注意:
當「服務器環」上連續兩臺服務器同時故障的時候,那麼這個系統就崩潰了
能夠對數據作兩次熱備份,以提升安全性,但性能和硬件利用率會有所損耗。
6.如何增長服務器?
首先須要經過配置讓這臺服務器知道節點環上的任意一臺服務器的IP地址(假設是10.0.0.1)
此服務端運行以後,他就會從10.0.0.1上獲取對照表,
以此知道本身在節點環中的具體位置,
它首先須要從它的下一個節點中遷移一部分數據(也就是它上一個節點熱備份的一部分數據)
而後從上一個節點中索取一部分數據(也就是該本身存儲的一部分數據)
而後它把本身加入對照表中,
而後告知10.0.0.1須要更新對照表,以此引起連鎖反應
並加入了我本身的想法(熱備機制、配置表保存及升級機制)
最終造成此文。
2014年4月9號:
第一個問題:此文利用IP地址(虛擬IP地址)計算哈希值的辦法尚待進一步考慮和驗證
第二個問題:增減服務器節點均是在"物理節點環"上完成,與「虛擬節點環」沒有關係
第三個問題:除了熱備,還能夠在熱備的基礎上實現負載均衡