1. CAP原則
又稱CAP定理,指的是在一個分布式系統中,一致性(Consistency)、可用性(Availability)、分區容錯性(Partition tolerance)。CAP 原則指的是,這三個要素最多只能同時實現兩點,不可能三者兼顧。
2. Raft算法
Nacos 集群為了保證集群中數據的一致性,其采用了 Raft 算法,是通過對日志進行復制管理來達到一致性的算法。
Raft 算法是強一致性算法。
Nacos 同時支持 AP 與 CP,默認情況下,Nacos 集群是 AP 的。
Raft算法將Server划分為三種角色:
- Leader:負責處理客戶端讀和寫請求的節點,同時負責日志復制工作,一個集群中只有一個Leader。
- Follower:可以處理客戶端讀請求,負責同步來自於 Leader 的日志,當接收到其它Cadidate 的投票請求后可以進行投票;當發現 Leader 掛了,其會轉變為 Candidate 發起Leader 選舉。
- Candidate:一種臨時的角色,只存在於leader的選舉階段(Leader 選舉的候選人),某個節點想要變成leader,那么就發起投票請求,同時自己變成candidate。如果選舉成功,則變為candidate,否則退回為follower
3.選舉
Raft中使用心跳機制來出發leader選舉。當服務器啟動的時候,服務器成為follower。只要follower從leader或者candidate收到有效的RPCs就會保持follower狀態。如果follower在一段時間內(該段時間被稱為election timeout)沒有收到消息,則它會假設當前沒有可用的leader,然后開啟選舉新leader的流程。
Term(任期)
任期用連續的數字進行表示。每一個任期的開始都是一次選舉(election),在某些情況下,有可能沒有選出Leader,那么,將會開始另一個任期,並且立刻開始下一次選舉。Raft 算法保證在一個任期內只有一個Leader.
過程
- follower增加當前的term;
- 轉變為candidate;
- 向自己投票;
- 向其它節點發出投票請求。
投票
- 發來投票請求 candidate 的 term 和 log 編號不能小於當前 candidate 的 term 和 log 編號;
- 當前 term 內 candidate 的票還沒投遞給自己(一個 term 內每個節點都只有一票 );
- 接收到多個投票請求時,采取先到先得投遞。
結果
當一個 Candidate 發出投票請求后會等待其它節點的響應結果。這個響應結果可能有三種情況:
- 收到過半選票,成為新的 leader。然后會將消息廣播給所有其它節點,產生新 Leader 了(其中包含其當前的 term);
- 接收到別的 candidate 發來的新 leader 通知,比較新 leader 的 term 是否不比當前的 term小,則自己轉變為 follower;
- 沒有收到過半選票,也沒有收到新 leader 通知,則重新選舉。
- 票數相同時,采取隨機選舉超時處理:讓這些 candidate 的選舉在一個給定范圍值內,各自隨機的 timeout 之后開始,此時先到達 timeout 的 candidate 會先發出投票請求,並優先獲取到投票。
4.數據同步/日志復制
主要作用是用於保證節點的一致性,這階段所做的操作也是為了保證一致性與高可用性。
Raft 把每條日志都附加了 任期號和下標 來保證日志的唯一性.
當Leader選舉出來后便開始負責客戶端的請求,所有事務(更新操作)請求都必須先經過Leader處理。
- 在Raft中當接收到客戶端的日志(事務請求)后先把該日志追加到本地的Log中;
- 然后通過 heartbeat 把該Entry同步給其他 Follower;
- Follower 接收到日志后記錄日志然后向 Leader 發送ACK;
- 當 Leader 收到大多數(n/2+1)Follower的ACK信息后將該日志設置為已提交並追加到本地磁盤中;
- 通知客戶端並在下個heartbeat中 Leader 將通知所有的Follower將該日志存儲在自己的本地磁盤中。
5.腦裂
在一個高可用系統中,當聯系着的節點因為網絡連接斷開聯系時,本來為一個整體的系統,分裂成兩個獨立節點,兩個節點開始爭搶共享資源造成系統混亂、數據損壞的現象,成為“腦裂”。
列如:FollowerA由於網絡問題感知不到Leader存在,FollowerA與FollowerB之間是相連的,此時FollowerA會發起選舉,雖然 FollowerB能夠感知到 Leader,但由於其接收到了更大 term 的投票請求,所以 FollowerB也就放棄了Leader,參與了新 Leader 的選舉。新Leader的寫請求並不會同步到原Leader節點上。而之前的Leader由於無法獲取過半響應而無法處理寫操作請求,不過並沒有被Down,其仍為 Leader。所以之前Leader的數據是不會發生變更的。此時就形成了數據的不一致。
解決方案:通過時間續約和term比較最終舊leader被同步為follower。