天天看點

第九章:Redis replication 主從複制

什麼是主從複制

  1. 一個master可以有多個slave
  2. 一個slave隻能有一個master
  3. 資料流是單向的,master到slave

全量複制和部分複制

run id 檢視複制偏移量(用來比對兩邊資料同步問題,相差不能太大)
  1. 插一個指令

    redis-cli -p 6379 info server | grep run

    檢視redis運作id
    第九章:Redis replication 主從複制
    image.png
  2. 檢視複制偏移量
    第九章:Redis replication 主從複制
    image.png
全量複制

在Redis複制的基礎上,使用和配置主從複制非常簡單,它允許從屬Redis伺服器成為主伺服器的精确副本。每次鍊路斷開時,從裝置将自動重新連接配接到主裝置,無論主裝置發生什麼情況,都将試圖成為主裝置的精确副本。

這個系統使用三個主要機制:

  1. 當主和從執行個體連接配接良好時,主裝置通過發送指令流來保持從裝置更新,以便複制對主資料集中發生的資料集的影響:客戶機寫入,密鑰過期或被驅逐等等。
  2. 當主站和從站之間的鍊路斷開時,對于網絡問題或者由于在主站或從站中感測到逾時,從站重新連接配接并嘗試進行部分重新同步:這意味着它将嘗試隻擷取部分在斷開連接配接時錯過的指令流。
  3. 當部分重新同步不可能時,從機将要求完全重新同步。這将涉及一個更複雜的過程,在這個過程中,主機需要建立所有資料的快照,将資料發送給從機,然後在資料集更改時繼續發送指令流。

Redis預設使用異步複制,這是高延遲和高性能,是絕大多數Redis用例的自然複制模式。 但是,Redis從站會異步确認主站定期收到的資料量。

某些資料的同步複制可以由用戶端使用WAIT指令來請求。 但WAIT隻能確定在其他Redis執行個體中具有指定數量的已确認副本:在故障轉移期間出于不同原因的故障轉移期間,确認寫入仍可能丢失,或取決于Redis持久性的确切配置。 您可以檢查Sentinel或Redis群集文檔以擷取有關高可用性和故障轉移的更多資訊。 本文的其餘部分主要描述了Redis基本複制的基本特征。

以下是關于Redis複制的一些非常重要的事實:

  • Redis使用異步複制,異步從到主機确認處理的資料量。
  • 主人可以有多個奴隸。
  • 從站能夠接受來自其他從站的連接配接。除了将多個從站連接配接到同一個主站之外,從站也可以以層疊狀結構連接配接到其他從站。自從Redis 4.0以來,所有的子從伺服器都會收到與主伺服器完全相同的複制流。
  • Redis複制在主端是非阻塞的。這意味着當一個或多個從機執行初始同步或部分重新同步時,主機将繼續處理查詢。
  • 複制在很大程度上也是非阻塞的。從伺服器執行初始同步時,它可以使用舊版本的資料集處理查詢,假定您在redis.conf中配置了Redis。否則,如果複制流已關閉,則可以将Redis從屬程式配置為向用戶端傳回錯誤。但是,在初始同步之後,必須删除舊資料集,并且必須加載新資料集。從站将在這個簡短的視窗中阻塞傳入的連接配接(對于非常大的資料集可能隻有很多秒)。自Redis 4.0以來,可以配置Redis,以便舊資料集的删除發生在不同的線程中,但是加載新的初始資料集仍然會在主線程中發生并阻止從屬。
  • 複制既可用于可伸縮性,也可用于隻讀查詢的多個從站(例如,可将低速O(N)操作解除安裝到從站),或者僅用于資料安全。
  • 可以使用複制來避免讓主伺服器将完整資料集寫入磁盤的成本:一種典型的技術包括配置主伺服器redis.conf以避免永久儲存到磁盤,然後連接配接配置為不時儲存的從伺服器或啟用AOF。然而,這個設定必須小心處理,因為重新啟動的主裝置将從一個空資料集開始:如果從裝置嘗試與其同步,則從裝置也将被清空。
當master當機的複制安全

在使用Redis複制的設定中,強烈建議在主伺服器和從伺服器中啟用持久性。如果這種情況不可行,例如由于磁盤速度非常慢導緻的延遲問題,則應配置執行個體以避免重新啟動後自動重新啟動。

為了更好地了解關閉配置為自動重新開機的主裝置是否危險的原因,請檢查以下故障模式,其中資料從主裝置及其所有從裝置擦除:

  1. 我們有一個設定,節點A作為主節點,持久性關閉,節點B和C從節點A複制。
  2. 節點A崩潰,但它有一些自動重新啟動系統,重新啟動過程。但是由于持久性被關閉,節點将重新啟動一個空的資料集。
  3. 節點B和C将從節點A複制,節點A是空的,是以它們将有效地銷毀它們的資料副本。

    當Redis Sentinel用于高可用性時,關閉主伺服器上的持久性以及程序的自動重新開機也是危險的。例如,主機可以很快重新開機,Sentinel不會檢測到故障,以便發生上述故障模式。

每次資料安全很重要,複制與配置為無持久性的主站一起使用時,應禁用執行個體的自動重新開機。

當Redis Sentinel用于高可用性時,關閉主伺服器上的持久性以及程序的自動重新開機也是危險的。 例如,主機可以很快重新開機,Sentinel不會檢測到故障,以便發生上述故障模式。

每次資料安全很重要,複制與配置為無持久性的主站一起使用時,應禁用執行個體的自動重新開機。

Redis複制如何工作

每個Redis master都有一個複制ID:它是一個大的僞随機字元串,标記資料集的給定故事。 每個主裝置也會獲得一個偏移量,該設定為生成的每個複制流位元組增加以發送到從裝置,以便使用修改資料集的新更改更新從裝置的狀态。 即使沒有從機連接配接,複制偏移量也會增加,是以基本上每一對給定的:

識别主資料集的确切版本。

當從站連接配接到主站時,它們使用PSYNC指令來發送它們的舊主站複制ID以及到目前為止處理的偏移量。這樣主人可以發送所需的增量部分。但是,如果主緩沖區中沒有足夠的積壓,或者從伺服器引用了不再知道的曆史記錄(複制辨別),則會發生完全重新同步:在這種情況下,從伺服器将獲得資料集的完整副本, 從頭開始​​。

這是完全同步如何更詳細地工作:

  • 主人開始一個背景儲存過程,以生成一個RDB檔案。同時開始緩沖從用戶端收到的所有新的寫入指令。當背景儲存完成後,主伺服器将資料庫檔案傳輸給從伺服器,将其儲存到磁盤上,然後将其加載到記憶體中。主機會将所有緩沖的指令發送給從機。這是作為指令流完成的,并且與Redis協定本身的格式相同。
  • 你可以通過telnet自己嘗試一下。在伺服器正在做一些工作的同時連接配接到Redis端口并發出SYNC指令。您将看到一個批量傳輸,然後主機接收到的每個指令都将在遠端登入會話中重新發出。實際上,SYNC是一個舊的協定,不再由較新的Redis執行個體使用,但仍然存在向後相容性:它不允許部分重新同步,是以現在使用PSYNC。
  • 如前所述,當主從鍊路出于某種原因關閉時,從站能夠自動重新連接配接。如果主站收到多個并發的從站同步請求,它将執行一次背景儲存,以便為它們提供全部服務。

無盤複制

通常情況下,完全重新同步需要在磁盤上建立一個RDB檔案,然後從磁盤重新加載相同的RDB,以便向從屬裝置提供資料。

對于較慢的磁盤,對于主裝置來說這可能是一個非常緊張的操作。 Redis 2.8.18版是第一個支援無盤複制的版本。 在此設定中,子程序直接通過線将RDB發送到從伺服器,而不使用磁盤作為中間存儲。

全量複制開銷

  • bgsave時間
  • RDB檔案網絡傳輸時間
  • 從節點清空資料時間
  • 從節點加載RDB時間
  • 可能的AOF重寫時間

部分複制

連接配接斷開時,master會寫一個複制緩沖區的指令,slave再連接配接master時候會把自己的偏量值offset和runid告訴master,如果丢失資料在buffer緩存的一個範圍内,則master把緩沖區隊列的資料給slave。然後再把部分資料同步給slave

複制的配置

slaveof指令
  1. 複制指令
slaveof 127.0.0.1 6380
           

丢棄舊資料集,轉而開始對新主伺服器進行同步。

  1. 取消複制
slaveof no one
           

将使得這個從屬伺服器關閉複制功能,并從從屬伺服器轉變回主伺服器,原來同步所得的資料集不會被丢棄。

配置

主要修改4個參數:

  1. port;
  2. logfile;
  3. slaveof;
  4. pidfile;
  5. daemonize(是否在背景執行)
然後再添加配置
slaveof ip port
slave-read-only yes #設定隻讀
           
兩種方式比較
方式 指令 配置
優點 無需重新開機 統一配置
缺點 不便于管理 需要重新開機
實戰
  1. 我配置了一個端口為6379,和端口為6380的服務,并在背景啟動
#6379配置
port 6379
pidfile /var/run/redis_6379.pid
# slaveof <masterip> <masterport>
logfile "6379.log"
daemonize yes


#6380配置
port 6380
pidfile /var/run/redis_6380.pid
slaveof 127.0.0.1 6379
masterauth xxxxx    #如果master有密碼,則需要設定
logfile "6380.log"
daemonize yes
           
  1. 第九章:Redis replication 主從複制
    對6379執行指令 info replication
    第九章:Redis replication 主從複制
    對6380執行指令 info replication
  2. 然後我在主機上set一個東西,在slave上擷取
    第九章:Redis replication 主從複制
    image.png
  3. 同步資料

在master的cli中執行

slaveof 127.0.0.1 6380