零、redis集群解決方案
1.Twitter開發的twemproxy
2.豌豆莢開發的codis
3.redis官方的redis-cluster
親兒子畢竟是更新最快,維護和支持新版本redis新特性好的,所以選擇方案上業界一般選擇redis-cluster
一、redis-cluster簡介
- redis-cluster是redis社區中推出的redis分布式集群解決方案
- 主要解決redis分布式的需求:
- 單機內存瓶頸
- 并發和流量瓶頸
- 同步復制帶寬瓶頸等
- redis3.0之后版本支持redis-cluster集群
- 至少需要3主(master)+3從(slave)才能建立集群
- redis-cluster 采用無中心結構(類比區塊鏈的去中心化)結構
每個節點保存數據和集群信息狀態,每個節點和其他節點連接
二、結構
每個節點保存數據和集群信息狀態,每個節點和其他節點連接
其結構特點:
1、所有的redis節點彼此互聯(PING-PONG機制),內部使用二進制協議優化傳輸速度和帶寬。
2、節點的fail是通過集群中超過半數的節點檢測失效時才生效。
3、客戶端與redis節點直連,不需要中間proxy層.客戶端不需要連接集群所有節點,連接集群中任何一個可用節點即可。
4、redis-cluster把所有的物理節點映射到[0-16383]slot上(不一定是平均分配),cluster 負責維護node<->slot<->value。
5、Redis集群預分好16384個桶,當需要在 Redis 集群中放置一個 key-value 時,根據 CRC16(key) mod 16384的值,決定將一個key放到哪個桶中。
三、容錯性
容錯性指軟件檢測應用程序所在運行的軟件或硬件中發生的錯誤并從錯誤中恢復的能力,通常可以從系統的可靠性,可用性,可測性的等幾方面來衡量。
- 1 什么時候判斷 master 不可用?
投票機制。投票過程是集群中所有 master 參與,如果半數以上 master 節點與 master節點通信超時(cluster-node-timeout)認為當前 master 節點掛掉
- 2 什么時候整個集群不可用(cluster state: fail)
如果集群任意 master 掛掉,且當前 master 沒有 slave。集群進入fail狀態也可以理解成集群的 Slot 映射 0-16383] 不完整時進入 fail 狀態。如果集群超過半數以上 master 掛掉,無論是否有 slave,集群進入 fail 狀態
四、節點分配(數據分片)
1.redis cluster節點分配**
現在我們是三個主節點分別是:A, B, C 三個節點,它們可以是一臺機器上的三個端口,也可以是三臺不同的服務器。那么,采用哈希槽 (hash slot)的方式來分配16384個slot 的話,它們三個節點分別承擔的slot 區間是:
節點A覆蓋0-5460;
節點B覆蓋5461-10922;
-
節點C覆蓋10923-16383.
獲取數據:
如果存入一個值,按照redis cluster哈希槽的算法: CRC16('key')384 = 6782。 那么就會把這個key 的存儲分配到 B 上了。同樣,當我連接(A,B,C)任何一個節點想獲取'key'這個key時,也會這樣的算法,然后內部跳轉到B節點上獲取數據
2.新增一個主節點:
新增一個節點D,redis cluster的這種做法是從各個節點的前面各拿取一部
分slot到D上,我會在接下來的實踐中實驗。大致就會變成這樣:
節點A覆蓋1365-5460
節點B覆蓋6827-10922
節點C覆蓋12288-16383
節點D覆蓋0-1364,5461-6826,10923-12287
同樣刪除一個節點也是類似,移動完成后就可以刪除這個節點了。
3.Redis Cluster主從模式
redis cluster 為了保證數據的高可用性,加入了主從模式,一個主節點對應一個或多個從節點,主節點提供數據存取,從節點則是從主節點拉取數據備份,當這個主節點掛掉后,就會有這個從節點選取一個來充當主節點,從而保證集群不會掛掉
上面那個例子里, 集群有ABC三個主節點, 如果這3個節點都沒有加入從節點,如果B掛掉了,我們就無法訪問整個集群了。A和C的slot也無法訪問。
所以我們在集群建立的時候,一定要為每個主節點都添加了從節點, 比如像這樣, 集群包含主節點A、B、C, 以及從節點A1、B1、C1, 那么即使B掛掉系統也可以繼續正確工作。
B1節點替代了B節點,所以Redis集群將會選擇B1節點作為新的主節點,集群將會繼續正確地提供服務。 當B重新開啟后,它就會變成B1的從節點。
不過需要注意,如果節點B和B1同時掛了,Redis集群就無法繼續正確地提供服務了。
五、安裝集群
對于下文中第七步創建集群時,版本之間的差異
- Redis 5 直接 用redis-cli
直接干就完了 - Redis version 3 or 4,
需要a.先安裝一個Ruby環境
b.再redis-trib.rb(ruby語言開發)的工具
Redis version 3 or 4可參考此處
redis5集群的安裝
1.創建Redis節點安裝目錄
mkdir -p /usr/local/redis-cluster
2.在redis-cluster目錄下,分別創建7000-7005個文件夾
mkdir 7000 7001 7002 7003 7004 7005
3.并將redis-conf拷貝到7000文件夾下
cp /opt/redis-5.0.7/redis-conf ./7000
4.分別修改redis配置文件
./7000/redis.conf
#關閉保護模式用 于公網訪問
protected-mode no
port 7000
#開啟集群模式
cluster-enabled yes
# 各個節點的配置文件,一定要根據端口進行分別設置,否則集群啟動不了
cluster-config-file nodes-{port}.conf
cluster-node-timeout 5000
# 后臺啟動
daemonize yes
pidfile /var/run/redis_7000.pid
logfile 7000.log
# 此處綁定 ip 可以是阿里內網 ip 和本地 ip 也可以直接注釋掉該項
#bind127.0.0.1
# 用于連接主節點密碼
masterauth fatsnake
#設置redis密碼各個節點請保持密碼一致
requirepass fatsnake
#設置節點持久化文件或是目錄名,讓各個節點分開:rdb文件名或者aof文件名
dbfilename dump_7000.rdb
appendfilename "appendonly_7000.aof"
#
5.依次修改并復制 6個redis.conf
cp ./7000/redis.conf ./7001/
vim ./7000/redis.conf
執行 :%s/oldPort/newPort/g 全局替換端口 :wq 保存并退出 即可
6.依次啟動6個節點
將安裝的 redis 目錄下的 src 復制到 cluster文件目錄下,方便啟動服務端
cd /opt/redis-5.0.7: 進入 redis 安裝目錄
cp -r ./src /usr/local/redid-cluster/ 將src文件復制到 redis- cluster 目錄中
./src/redis-server ./7000/redis.conf
./src/redis-server ./7001/redis.conf
./src/redis-server ./7002/redis.conf
./src/redis-server ./7003/redis.conf
./src/redis-server ./7004/redis.conf
./src/redis-server ./7005/redis.conf
啟動后,可以用 PS 查看進程:
ps -ef | grep redis
啟動后效果:
7.創建集群通信(見上文版本差異)
redis5版本以后使用redis-cli客戶端來創建集群
-a 參數為 集群密碼
./src/redis-cli --cluster create -a fatsnake 127.0.0.1:7000 127.0.0.1:7001 \
127.0.0.1:7002 127.0.0.1:7003 127.0.0.1:7004 127.0.0.1:7005 \
--cluster-replicas 1
cluster-replicas 1 代表 一個master后有幾個slave,1代表為1個slave節點
詢問是否滿意如此分配節點:輸入yes之后,如圖顯示表示集群創建成功
六、redis-cluster集群驗證
再描述一遍集群特點
Redis cluster 為了保證數據的高可用性,加入了主從模式,一個主節點對應一個或多個從節點
主節點提供數據存取,從節點則是從主節點拉取數據備份,從節點提供查詢
當這個主節點掛掉后,就會有這個從節點選取一個來充當主節點,從而保證集群不會掛掉
-
集群如果有 ABC 三個主節點如果這 3 個節點都沒有加入從節點,如果 B 桂掉了,我們就無法訪問整個集群了。A 和C的slot(哈希槽) 也無法訪問。
所以我們在集群建立的時候,一定要為每個主節點都添加了從節點,比如像這樣集群包含主節點 A、B、C,以及
從節點 A1、B1、C1, 那么即使 B 掛掉系統也可以繼續正確工作。
B1 節點替代了 B 節點,所以 Redis 集群將會選擇 B1 節點作為新的主節點,集群將會繼續正確地提供服務。當 B 重新開啟后,它就會變成 B1 的從節點。
不過需要注意,如果節點 B 和 B1 同時掛了,Redis 集群就無法繼續正確地提供服務了。連接集群中的某個節點,驗證
redis-cli -h 127.0.0.1 -c -p 7000 -a fatsnake
參數說明:
-h : ip
-c : 添加此參數,可連接到集群
-a :集群密碼
redis cluster 在設計的時候,就考慮到了去中心化,去中間件,也就是說,集群中的每個節點都是平等的關系,都是對等的,每個節點都保存各自的數據和整個集群的狀態。毎個節點都和其他所有節點連接,而這些連接保持活躍,這樣就保證了我們只需要連接集群中的任意一個節點,就可以獲取到其他節點的數據
基本命令
查看單節點狀態
info replication
查看集群狀態
Cluster Nodes 命令 或者 Cluster Infor
說明:
myself 表示當前 操作節點
唯一性節點ID說明:
- 每個 Redist 的節點都有一個 ID 值,此 ID 將被此特定 redis 實例永久使用,以便實例在集群上下文中具有唯一的名稱。
- 每個節點都會記住使用此 ID 的每個其他節點,而不是通過 IP 或端口。
- IP 地址和端口可能會發生變化,但唯一的節點標識符在節點的整個生命周期內都不會改變。我們簡單地稱這個標識符為節點 ID。