redis cluster介紹
從redis3.0.0開始,官方支持了redis cluster的集群模式,結束了redis沒有集群的時代。
redis cluster實現(hash slot算法)
Redis 集群沒有並使用傳統的一致性哈希來分配數據,而是采用另外一種叫做哈希槽 (hash slot)
的方式來分配的。redis cluster 默認分配了 16384 個slot,當我們set一個key 時,會用CRC16
算法來取模得到所屬的slot
,然后將這個key 分到哈希槽區間的節點上,具體算法就是:CRC16(key) % 16384
。
(為什么是16384,選取了16384是因為crc16會輸出16bit的結果,可以看作是一個分布在0-2^16-1之間的數,redis的作者測試發現這個數對2^14求模的會將key在0-2^14-1之間分布得很均勻,因此選了這個值。)
在構建redis cluster集群時,master必須大於等於3,否則會創建失敗。並且,當集群中存活的master節點數小於總節點數的一半的話,集群就無法提供服務了。
例:我們有三個master節點A、B、C,采用哈希槽 (hash slot)
的方式來分配16384個slot 的話,它們三個節點分別承擔的slot 區間是:
節點A:0 ~ 5460 節點B:5461 ~ 10922 節點C:10923 ~ 16383
節點在收到讀寫請求時,會根據CRC16(key) % 16384算出的槽號去查是否指向自己,如果是則進行處理,如果不是,則返回moved錯誤,moved錯誤攜帶正確的節點IP和端口號返回客戶端並指引其轉向執行,而后客戶端每次關於該key都會去moved返回的節點執行。
當節點的key正在遷移的時候,收到關於該key的請求,那么節點會返回ask錯誤,並但會正確的節點ip和端口號給客戶端去執行。但是這個轉向只對本次請求有效,后面關於該key的請求還是會發送到目前正在處理key遷移的節點,直到key遷移完畢並發送廣播通知。
當有新節點D加入時,redis cluster的這種做法是從各個節點的前面各拿取一部分slot到D
上。會變成下面這樣:
節點A:1364 ~ 5460 節點B:6826 ~ 10922 節點C:12287 ~ 16383 節點D:0 ~ 1364, 5461 ~ 6826, 10923 ~ 12287
刪除節點也是類似,數據會均勻的遷移到剩余節點上,遷移完成后就可以刪除這個節點了。
cluster節點通信
redis cluster的構造類似下圖所示
在 redis cluster 架構下,每個 redis 要放開兩個端口號,比如一個是 6379,另外一個就是 加1w 的端口號,比如 16379。
16379 端口號是用來進行節點間通信的,也就是 cluster bus 的東西,cluster bus 的通信,用來進行故障檢測、配置更新、故障轉移授權。cluster bus 用了另外一種二進制的協議,gossip 協議,用於節點間進行高效的數據交換,占用更少的網絡帶寬和處理時間。
主從模式
redis cluster 為了保證數據的高可用性,加入了主從模式,一個主節點對應一個或多個從節點,主節點提供數據存取,從節點則是從主節點拉取數據備份,當這個主節點掛掉后,就會有這個從節點選取一個來充當主節點,從而保證集群不會掛掉。
不過redis的cluster模式不支持主從的樹狀結構。
主從模式最經典的是哨兵(Sentinel)模式,而Sentinel模式需要至少三台機器(一主二從三哨兵),而cluster模式建議每個master最好部署在不同的物理機上,所以,算一算搭建一個高可用的redis cluster至少需要九台物理機……