1、主從java
經過持久化功能,Redis保證了即便在服務器重啓的狀況下也不會損失(或少許損失)數據,由於持久化會把內存中數據保存到硬盤上,重啓會從硬盤上加載數據。
。可是因爲數據是存儲在一臺服務器上的,若是這臺服務器出現硬盤故障等問題,也會致使數據丟失。爲了不單點故障,一般的作法是將數據庫複製多個副本以部署在不一樣的服務器上,這樣即便有一臺服務器出現故障,其餘服務器依然能夠繼續提供服務。爲此, Redis 提供了複製(replication)功能,能夠實現當一臺數據庫中的數據更新後,自動將更新的數據同步到其餘數據庫上。node
在複製的概念中,數據庫分爲兩類,一類是主數據庫(master),另外一類是從數據庫[1] (slave)。主數據庫能夠進行讀寫操做,當寫操做致使數據變化時會自動將數據同步給從數據庫。而從數據庫通常是隻讀的,並接受主數據庫同步過來的數據。一個主數據庫能夠擁有多個從數據庫,而一個從數據庫只能擁有一個主數據庫。redis
master slave
主不用配置,從redis的conf文件加入 slaveof ip port 就能夠了
或者從redis啓動時 redis-server --port 6380 --slaveof 127.0.0.1 6379 從數據庫通常是隻讀,能夠改成可寫,但寫入的數據很容易被主同步沒,因此仍是隻讀就能夠。
也能夠在運行是使用slaveof ip port命令,中止原來的主,切換成剛剛設置的主 slaveof no one會把本身變成主數據庫
當從數據庫啓動時,會向主數據庫發送sync命令,主數據庫接收到sync後開始在後臺報錯快照rdb,在保存快照期間受到的命名緩存起來,當快照完成時,主數據庫會將快照和緩存的命令一塊發送給從。複製初始化結束。以後,主每受到1個命令就同步發送給從。
當出現斷開重連後,2.8以後的版本會將斷線期間的命令傳給重數據庫。增量複製緩存
主從複製是樂觀複製,當客戶端發送寫執行給主,主執行完當即將結果返回客戶端,並異步的把命令發送給從,從而不影響性能。也能夠設置至少同步給多少個從主纔可寫。
無硬盤複製:若是硬盤效率低將會影響複製性能,2.8以後能夠設置無硬盤複製,repl-diskless-sync yes安全
2、哨兵ruby
當主數據庫遇到異常中斷服務後,開發者能夠經過手動的方式選擇一個從數據庫來升格爲主數據庫,以使得系統可以繼續提供服務。然而整個過程相對麻煩且須要人工介入,難以實現自動化。 爲此,Redis 2.8中提供了哨兵工具來實現自動化的系統監控和故障恢復功能。
哨兵的做用就是監控redis主、從數據庫是否正常運行,主出現故障自動將從數據庫轉換爲主數據庫。服務器
顧名思義,哨兵的做用就是監控Redis系統的運行情況。它的功能包括如下兩個。併發
(1)監控主數據庫和從數據庫是否正常運行。
(2)主數據庫出現故障時自動將從數據庫轉換爲主數據庫。less
能夠用info replication查看主從狀況
例子:
1主2從 1哨兵,能夠用命令起也能夠用配置文件裏
可使用雙哨兵,更安全,
redis-server --port 6379
redis-server --port 6380 --slaveof 192.168.0.167 6379
redis-server --port 6381 --slaveof 192.168.0.167 6379
redis-sentinel sentinel.conf
哨兵配置文件
sentinel.conf
sentinel monitor mymaster 192.168.0.167 6379 1
其中mymaster表示要監控的主數據庫的名字,能夠本身定義一個。這個名字必須僅由大小寫字母、數字和「.-_」這 3 個字符組成。後兩個參數表示主數據庫的地址和端口號,這裏咱們要監控的是主數據庫6379。
注意:
一、使用時不能用127.0.0.1,須要用真實IP,否則java程序經過哨兵會連到java程序所在的機器(127.0.0.1 )
二、配置哨兵監控一個系統時,只須要配置其監控主數據庫便可,哨兵會自動發現全部複製該主數據庫的從數據庫
這樣哨兵就能監控主6379和從6380、6381,一旦6379掛掉,哨兵就會在2個從中選擇一個做爲主,根據優先級選,若是同樣就選個id小的,當6379再起來就做爲從存在。
主從切換過程:
(1) slave leader升級爲master
(2) 其餘slave修改成新master的slave
(3) 客戶端修改鏈接
(4) 老的master若是重啓成功,變爲新master的slave
哨兵監控1主2從,停掉主,哨兵會選出1個從做爲主,變成1主1從。然而當我把原來的主再起來,它不會做爲從,只是個獨立的節點。
若是在新的主剛被選出來時,我把原來的主起來,它就能成爲新主的從節點。
若是在新的主選出來過一會再起原來的主,就不能成爲新主的從節點
或者在老的主起來後,重啓哨兵也能把它變成從,哨兵配置文件裏有,哨兵會執行「+convert-to-slave」
這很奇怪,我也沒弄明白是怎麼回事。
即便使用哨兵,redis每一個實例也是全量存儲,每一個redis存儲的內容都是完整的數據,浪費內存且有木桶效應。爲了最大化利用內存,能夠採用集羣,就是分佈式存儲。即每臺redis存儲不一樣的內容,
共有16384個slot。每一個redis分得一些slot,hash_slot = crc16(key) mod 16384 找到對應slot,鍵是可用鍵,若是有{}則取{}內的做爲可用鍵,不然整個鍵是可用鍵
集羣至少須要3主3從,且每一個實例使用不一樣的配置文件,主從不用配置,集羣會本身選。
修改每一個實例的配置文件:
cluster-enabled yes --開啓集羣
cluster-config-file nodes-6382.conf --集羣配置文件名,每一個實例配置的要不一樣,redis會根據文件名自動新建
用集羣工具建立集羣:
咱們能夠用集羣工具進行集羣,該工具是redis源碼包中,用ruby編寫,因此須要先安裝ruby。
一、安裝rubygems
yum install ruby
yum install rubygems
gem install redis
二、把6個redis實例都起來,每一個實例的集羣都打開。
三、redis安裝目錄的src執行./redis-trib.rb create --replicas 1 127.0.0.1:6380 127.0.0.1:6381 127.0.0.1:6382 127.0.0.1:6383 127.0.0.1:6384 127.0.0.1:6385
提示信息以下
Connecting to node 127.0.0.1:6380: OK Connecting to node 127.0.0.1:6381: OK Connecting to node 127.0.0.1:6382: OK Connecting to node 127.0.0.1:6383: OK Connecting to node 127.0.0.1:6384: OK Connecting to node 127.0.0.1:6385: OK >>> Performing hash slots allocation on 6 nodes... Using 3 masters: 127.0.0.1:6380 127.0.0.1:6381 127.0.0.1:6382 Adding replica 127.0.0.1:6383 to 127.0.0.1:6380 Adding replica 127.0.0.1:6384 to 127.0.0.1:6381 Adding replica 127.0.0.1:6385 to 127.0.0.1:6382 M: d4f906940d68714db787a60837f57fa496de5d12 127.0.0.1:6380 slots:0-5460 (5461 slots) master M: b547d05c9d0e188993befec4ae5ccb430343fb4b 127.0.0.1:6381 slots:5461-10922 (5462 slots) master M: 887fe91bf218f203194403807e0aee941e985286 127.0.0.1:6382 slots:10923-16383 (5461 slots) master S: e0f6559be7a121498fae80d44bf18027619d9995 127.0.0.1:6383 replicates d4f906940d68714db787a60837f57fa496de5d12 S: a61dbf654c9d9a4d45efd425350ebf720a6660fc 127.0.0.1:6384 replicates b547d05c9d0e188993befec4ae5ccb430343fb4b S: 551e5094789035affc489db267c8519c3a29f35d 127.0.0.1:6385 replicates 887fe91bf218f203194403807e0aee941e985286 Can I set the above configuration? (type 'yes' to accept):
輸入yes,這樣集羣就創建了。
登陸任一臺redis,執行 info cluster,提示cluster_enabled:1
集羣過程:
首先redis-trib.rb會以客戶端的形式嘗試鏈接全部的節點,併發送PING命令以肯定節點可以正常服務。若是有任何節點沒法鏈接,則建立失敗。同時發送 INFO 命令獲取每一個節點的運行ID以及是否開啓了集羣功能(即cluster_enabled爲1)。 準備就緒後集羣會向每一個節點發送 CLUSTER MEET命令,格式爲 CLUSTER MEET ip port,這個命令用來告訴當前節點指定ip和port上在運行的節點也是集羣的一部分,從而使得6個節點最終能夠納入一個集羣。
而後redis-trib.rb會分配主從數據庫節點,分配的原則是儘可能保證每一個主數據庫運行在不一樣的IP地址上,同時每一個從數據庫和主數據庫均不運行在同一IP地址上,以保證系統的容災能力
3主3從,當1個主故障,你們會給對應的從投票,把從立爲主,若沒有從數據庫能夠恢復則redis集羣就down了。
客戶端鏈接:
使用redis-cli -c -p 任意一個端口