【Redis】Redis 主從複製之一

楊奇龍發表於2016-05-25
前言
  和關係型資料庫一樣,Redis也有自己的高可用屬性,主從複製,相比而言 redis的主從複製的搭建過程更為簡單。
一 redis 主從複製的特點
1 同一個master可以擁有多個slaves。
2 master下的Slave還可以接受同一架構中其它slave的連結與同步請求,實現資料的級聯複製,即master->slave->Sslave模式;
3 master以非阻塞的方式同步資料至slave,這將意味著master會繼續處理一個或多個slave的讀寫請求;
4 slave端同步資料也可以修改為非阻塞是的方式,當slave在執行新的同步時,它仍可以用舊的資料資訊來提供查詢;否則,當slave與master失去聯絡時,slave會返回一個錯誤給客戶端;
5 redis的主從複製具有可擴充套件性,即多個slave專門提供只讀查詢與資料的冗餘,master端專門提供寫操作,實現讀寫分離,負載均衡;
6透過配置禁用Master資料持久化機制,將其資料持久化操作交給Slaves完成,避免在Master中要有獨立的程式來完成此操作。

二 redis 複製的原理以及注意事項
 我們可以從slave redis 的log中檢視redis 複製的主要過程
  1. [3308] 24 May 23:09:44.133 * Connecting to MASTER 10.0.2.8:6379
  2. [3308] 24 May 23:09:44.134 * MASTER <-> SLAVE sync started
  3. [3308] 24 May 23:09:44.134 * Non blocking connect for SYNC fired the event.
  4. [3308] 24 May 23:09:44.136 * Master replied to PING, replication can continue...
  5. [3308] 24 May 23:09:44.137 * Partial resynchronization not possible (no cached master)
  6. [3308] 24 May 23:09:44.137 * Full resync from master: 295a0c0dbf70e9b372ebdf6d14b0cae90072ac89:1
  7. [3308] 24 May 23:09:44.143 * MASTER <-> SLAVE sync: receiving 40 bytes from master
  8. [3308] 24 May 23:09:44.144 * MASTER <-> SLAVE sync: Flushing old data
  9. [3308] 24 May 23:09:44.144 * MASTER <-> SLAVE sync: Loading DB in memory
  10. [3308] 24 May 23:09:44.144 * MASTER <-> SLAVE sync: Finished with success
  11. [3308] 24 May 23:24:44.033 * 1 changes in 900 seconds. Saving...
  12. [3308] 24 May 23:24:44.034 * Background saving started by pid 3385
  13. [3385] 24 May 23:24:44.037 * DB saved on disk
  14. [3385] 24 May 23:24:44.038 * RDB: 0 MB of memory used by copy-on-write
  15. [3308] 24 May 23:24:44.134 * Background saving terminated with success
結合redis 主從同步的日誌和官方文件,我們總結一下redis的同步過程原理:
1 當一個redis 例項加上slaveof master_ip port 方式啟動時,無論是第一次連線還是重連,它會主向master傳送一個SYNC command,請求同步連線。
2 當master 收到SYNC 命令之後,傳送一個PING 命令給slave ,且在後臺執行bgsave命令,將資料快照儲存到資料檔案中,同時會記錄所有修改資料的命令並快取在資料檔案。
3 master後臺程式把資料持久化到磁碟之後,就傳送資料庫檔案給slave。
4 slave端將資料檔案儲存到硬碟上,然後將其在載入到記憶體中,完成第一次全量同步操作。
5 master會將之前收集到的修改資料的操作和新的修改資料的操作傳送給Slave端。
6 slave 收到這些命令之後會在本地執行,類似於MySQL的sql_thread操作。從而達到主從資料最終一致。
7 如果master和slave之間的連結出現斷連,slave可以自動重連master。根據版本的不同,斷連後同步的方式也不同:
    2.8之前:重連成功之後,一次全量同步操作將被自動執行.
    2.8之後:重連成功之後,進行部分同步操作.
Master持久化功能關閉時Replication的安全性
當我們部署redis主從複製的時候,一般都會強烈建議把master的持久化開關開啟。即使為了避免持久化帶來的延遲影響,不把持久化開關開啟,那麼也應該把master配置為不會自動啟動的。因為master異常crash後再重啟是非常危險的,會導致slave中的資料會被清空。
假設我們有一個redis節點A,設定為master,並且關閉持久化功能,另外兩個節點B和C是它的slave,並從A複製資料。
如果A節點崩潰了導致所有的資料都丟失了,它會有重啟系統來重啟程式。但是由於持久化功能被關閉了,所以即使它重啟了,它的資料集是空的。
而B和C依然會透過replication機制從A複製資料,所以B和C會從A那裡複製到一份空的資料集,並用這份空的資料集將自己本身的非空的資料集替換掉。於是就相當於丟失了所有的資料。
即使使用一些HA工具,比如說sentinel來監控master-slaves叢集,也會發生上述的情形,因為master可能崩潰後迅速恢復。速度太快而導致sentinel無法察覺到一個failure的發生。
部分同步(partial resynchronization )
這個特殊將會使用PSYNC 命令,注意該命令在2.8之後才支援PSYNC如果一個salve使用的是老的版本僅支援SYNC命令,那麼將會用SYNC來同步
無磁碟的複製
通常一個同步需要在磁碟上建立一個RDB檔案,然後再重新載入這個檔案來進行與slave資料同步
由於磁碟的讀寫是非常慢的,這對於redis master是一個非常有壓力的操作,在2.8.18之後的第一個版來嘗試使用無磁碟的複製,在這個設定裡了程式直接把RDB 傳送到slaves,而不需要使用磁碟來做中間的儲存。
需要注意的是 不過這個功能目前處於實驗階段,還未正式釋出。
三  部署主從複製
環境 :
rac4 主庫 10.0.2.8:6379
rac3 從庫 10.0.2.6:6379
1 在兩臺機器上或者同一臺機器起不同的埠,具體步驟請參考《redis 初探》
2 修改rac3 的redis.cnf 新增配置 ,指向rac4
  slaveof 10.0.2.8 6379 
  也可以在rac3上啟動redis之後執行
  slaveof 10.0.2.8 6379 
  不過一旦slave重啟之後 主從關係就消失了。建議在redis.cnf 配置
3 啟動主庫和從庫
  /usr/local/bin/redis-server /etc/redis/redis.conf
至此 搭建一個以rac4為主庫 ,rac3為從庫的redis 複製系統。
四 應用案例
主庫

  1. root@rac4:~# >redis-cli
  2. 127.0.0.1:6379> select 0
  3. OK
  4. 127.0.0.1:6379> set name yangyi
  5. OK
  6. 127.0.0.1:6379> get name
  7. "yangyi"
  8. 127.0.0.1:6379>
從庫
  1. root@rac3:~# >redis-cli
  2. 127.0.0.1:6379> select 0
  3. OK
  4. 127.0.0.1:6379> get name
  5. "yangyi"
  6. 127.0.0.1:6379>
五 推薦文章
    文章篇幅和時間有限,本文並未完整的介紹Redis的高可用特性,後續研究之後會陸續補充完整。 推薦《》,留一個(小白的)問題 ,redis主從複製過程和持久化的方式之間有什麼關係嗎 ,基於rdb 或者 aof的持久化 對主從複製有什麼影響? 

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/22664653/viewspace-2106349/,如需轉載,請註明出處,否則將追究法律責任。

相關文章