Redis基礎:容器化方式的主從模式

Redis有主從、哨兵和集羣三種常見模式,這篇文章使用Docker來說明Redis的主從模式的使用方式。

主從模式

在這裏插入圖片描述
主從模式之下,一般常見的方式Master負責寫,SLAVE負責讀。Redis提供了複製(Replication)功能用於數據同步,一個常見的流程如下所示:
在這裏插入圖片描述

  • 從數據庫連接主數據庫,發送SYNC命令;
  • 主數據庫接收到SYNC命令後,開始執行BGSAVE命令生成RDB文件並使用緩衝區記錄此後執行的所有寫命令;
  • 主數據庫BGSAVE執行完後,向所有從數據庫發送快照文件,並在發送期間繼續記錄被執行的寫命令;
  • 從數據庫收到快照文件後丟棄所有舊數據,載入收到的快照;
  • 主數據庫快照發送完畢後開始向從數據庫發送緩衝區中的寫命令;
  • 從數據庫完成對快照的載入,開始接收命令請求,並執行來自主數據庫緩衝區的寫命令;(從數據庫初始化完成)
  • 主數據庫每執行一個寫命令就會向從數據庫發送相同的寫命令,從數據庫接收並執行收到的寫命令(從數據庫初始化完成後的操作)
  • 出現斷開重連後,2.8之後的版本會將斷線期間的命令傳給重數據庫,增量複製。
  • 主從剛剛連接的時候,進行全量同步;全同步結束後,進行增量同步。當然,如果有需要,slave 在任何時候都可以發起全量同步。Redis 的策略是,無論如何,首先會嘗試進行增量同步,如不成功,要求從機進行全量同步。

構建主從模式的Redis環境

本文將使用6.0.4的Redis的官方鏡像爲例,使用docker-compose一鍵生成一個一主兩叢的Redis集羣。

docker-compose.yml

liumiaocn:redis liumiao$ cat docker-compose.yml 
version: '2'
services:
  # redis master
  master:
    image: redis:6.0.4
    container_name: redis-master
    restart: always
    command: redis-server --port 6379 --requirepass liumiaocn@server  --appendonly yes
    ports:
      - 6379:6379
    volumes:
      - ./data:/data

  # redis slave 1 
  slave1:
    image: redis:6.0.4
    container_name: redis-slave-1
    restart: always
    command: redis-server --slaveof 192.168.31.242 6379 --port 6380  --requirepass liumiaocn@slave1 --masterauth liumiaocn@server  --appendonly yes
    ports:
      - 6380:6380
    volumes:
      - ./data:/data

  # redis slave 2 
  slave2:
    image: redis:6.0.4
    container_name: redis-slave-2
    restart: always
    command: redis-server --slaveof 192.168.31.242 6379 --port 6381  --requirepass liumiaocn@slave2 --masterauth liumiaocn@server  --appendonly yes
    ports:
      - 6381:6381
    volumes:
      - ./data:/data
liumiaocn:redis liumiao$ 

代碼說明

  • requirepass:指定密碼,使用redis-cli連接進行操作時需要首先使用auth進行驗證
  • appendonly:開啓redis的數據持久化
  • masterauth:Slave端設定,需要與Master指定的密碼一致,否則無法連接成功
  • slaveof:Slave端設定,指定連接的Master的IP和端口號,也需要與Master保持一致

啓動

liumiaocn:redis liumiao$ docker-compose up -d
Creating network "redis_default" with the default driver
Creating redis-master  ... done
Creating redis-slave-1 ... done
Creating redis-slave-2 ... done
liumiaocn:redis liumiao$

啓動確認

liumiaocn:redis liumiao$ docker-compose ps
    Name                   Command               State                Ports              
-----------------------------------------------------------------------------------------
redis-master    docker-entrypoint.sh redis ...   Up      0.0.0.0:6379->6379/tcp          
redis-slave-1   docker-entrypoint.sh redis ...   Up      6379/tcp, 0.0.0.0:6380->6380/tcp
redis-slave-2   docker-entrypoint.sh redis ...   Up      6379/tcp, 0.0.0.0:6381->6381/tcp
liumiaocn:redis liumiao$ 
liumiaocn:redis liumiao$ 
liumiaocn:redis liumiao$ docker ps
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                              NAMES
313a21d3c602        redis:6.0.4         "docker-entrypoint.s…"   14 seconds ago      Up 13 seconds       6379/tcp, 0.0.0.0:6380->6380/tcp   redis-slave-1
50243006a963        redis:6.0.4         "docker-entrypoint.s…"   14 seconds ago      Up 13 seconds       6379/tcp, 0.0.0.0:6381->6381/tcp   redis-slave-2
d4b577332c5f        redis:6.0.4         "docker-entrypoint.s…"   14 seconds ago      Up 13 seconds       0.0.0.0:6379->6379/tcp             redis-master
liumiaocn:redis liumiao$ 

連接過程確認

Master日誌

從如下日誌的最後兩行可以看到,Master端已經成功與兩個Slave進行了連接

liumiaocn:redis liumiao$ docker-compose logs master
Attaching to redis-master
redis-master | 1:C 06 Jun 2020 00:44:10.566 # oO0OoO0OoO0Oo Redis is starting oO0OoO0OoO0Oo
redis-master | 1:C 06 Jun 2020 00:44:10.566 # Redis version=6.0.4, bits=64, commit=00000000, modified=0, pid=1, just started
redis-master | 1:C 06 Jun 2020 00:44:10.566 # Configuration loaded
redis-master | 1:M 06 Jun 2020 00:44:10.573 * Running mode=standalone, port=6379.
redis-master | 1:M 06 Jun 2020 00:44:10.573 # WARNING: The TCP backlog setting of 511 cannot be enforced because /proc/sys/net/core/somaxconn is set to the lower value of 128.
redis-master | 1:M 06 Jun 2020 00:44:10.573 # Server initialized
redis-master | 1:M 06 Jun 2020 00:44:10.573 # WARNING you have Transparent Huge Pages (THP) support enabled in your kernel. This will create latency and memory usage issues with Redis. To fix this issue run the command 'echo never > /sys/kernel/mm/transparent_hugepage/enabled' as root, and add it to your /etc/rc.local in order to retain the setting after a reboot. Redis must be restarted after THP is disabled.
redis-master | 1:M 06 Jun 2020 00:44:10.576 * Ready to accept connections
redis-master | 1:M 06 Jun 2020 00:44:10.606 * Replica 192.168.240.1:6380 asks for synchronization
redis-master | 1:M 06 Jun 2020 00:44:10.606 * Full resync requested by replica 192.168.240.1:6380
redis-master | 1:M 06 Jun 2020 00:44:10.606 * Replication backlog created, my new replication IDs are '543ebff4abe27ada53fd7d1f3c0cf1cf55dc0476' and '0000000000000000000000000000000000000000'
redis-master | 1:M 06 Jun 2020 00:44:10.606 * Starting BGSAVE for SYNC with target: disk
redis-master | 1:M 06 Jun 2020 00:44:10.607 * Background saving started by pid 19
redis-master | 1:M 06 Jun 2020 00:44:10.612 * Replica 192.168.240.1:6381 asks for synchronization
redis-master | 1:M 06 Jun 2020 00:44:10.612 * Full resync requested by replica 192.168.240.1:6381
redis-master | 1:M 06 Jun 2020 00:44:10.612 * Waiting for end of BGSAVE for SYNC
redis-master | 19:C 06 Jun 2020 00:44:10.615 * DB saved on disk
redis-master | 19:C 06 Jun 2020 00:44:10.615 * RDB: 0 MB of memory used by copy-on-write
redis-master | 1:M 06 Jun 2020 00:44:10.679 * Background saving terminated with success
redis-master | 1:M 06 Jun 2020 00:44:10.686 * Synchronization with replica 192.168.240.1:6380 succeeded
redis-master | 1:M 06 Jun 2020 00:44:10.688 * Synchronization with replica 192.168.240.1:6381 succeeded
liumiaocn:redis liumiao$ 

Slave日誌

以Slave 1爲例,從如下日誌中可以看到其與Master節點連接和數據同步的過程。

liumiaocn:redis liumiao$ docker-compose logs slave1
Attaching to redis-slave-1
redis-slave-1 | 1:C 06 Jun 2020 00:44:10.588 # oO0OoO0OoO0Oo Redis is starting oO0OoO0OoO0Oo
redis-slave-1 | 1:C 06 Jun 2020 00:44:10.588 # Redis version=6.0.4, bits=64, commit=00000000, modified=0, pid=1, just started
redis-slave-1 | 1:C 06 Jun 2020 00:44:10.588 # Configuration loaded
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.591 * Running mode=standalone, port=6380.
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.591 # WARNING: The TCP backlog setting of 511 cannot be enforced because /proc/sys/net/core/somaxconn is set to the lower value of 128.
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.591 # Server initialized
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.591 # WARNING you have Transparent Huge Pages (THP) support enabled in your kernel. This will create latency and memory usage issues with Redis. To fix this issue run the command 'echo never > /sys/kernel/mm/transparent_hugepage/enabled' as root, and add it to your /etc/rc.local in order to retain the setting after a reboot. Redis must be restarted after THP is disabled.
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.595 * Ready to accept connections
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.595 * Connecting to MASTER 192.168.31.242:6379
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.595 * MASTER <-> REPLICA sync started
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.596 * Non blocking connect for SYNC fired the event.
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.599 * Master replied to PING, replication can continue...
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.604 * Partial resynchronization not possible (no cached master)
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.610 * Full resync from master: 543ebff4abe27ada53fd7d1f3c0cf1cf55dc0476:0
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.684 * MASTER <-> REPLICA sync: receiving 175 bytes from master to disk
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.902 * MASTER <-> REPLICA sync: Flushing old data
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.902 * MASTER <-> REPLICA sync: Loading DB in memory
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.907 * Loading RDB produced by version 6.0.4
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.908 * RDB age 0 seconds
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.908 * RDB memory usage when created 1.88 Mb
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.908 * MASTER <-> REPLICA sync: Finished with success
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.910 * Background append only file rewriting started by pid 19
redis-slave-1 | 1:S 06 Jun 2020 00:44:10.941 * AOF rewrite child asks to stop sending diffs.
redis-slave-1 | 19:C 06 Jun 2020 00:44:10.941 * Parent agreed to stop sending diffs. Finalizing AOF...
redis-slave-1 | 19:C 06 Jun 2020 00:44:10.941 * Concatenating 0.00 MB of AOF diff received from parent.
redis-slave-1 | 19:C 06 Jun 2020 00:44:10.944 * SYNC append only file rewrite performed
redis-slave-1 | 19:C 06 Jun 2020 00:44:10.944 * AOF rewrite: 0 MB of memory used by copy-on-write
redis-slave-1 | 1:S 06 Jun 2020 00:44:11.001 * Background AOF rewrite terminated with success
redis-slave-1 | 1:S 06 Jun 2020 00:44:11.003 * Residual parent diff successfully flushed to the rewritten AOF (0.00 MB)
redis-slave-1 | 1:S 06 Jun 2020 00:44:11.004 * Background AOF rewrite finished successfully
redis-slave-1 | 1:S 06 Jun 2020 00:52:18.352 # Connection with master lost.
redis-slave-1 | 1:S 06 Jun 2020 00:52:18.352 * Caching the disconnected master state.
redis-slave-1 | 1:S 06 Jun 2020 00:58:53.300 * Connecting to MASTER 192.168.31.242:6379
redis-slave-1 | 1:S 06 Jun 2020 00:58:53.300 * MASTER <-> REPLICA sync started
redis-slave-1 | 1:S 06 Jun 2020 00:58:53.300 * Non blocking connect for SYNC fired the event.
redis-slave-1 | 1:S 06 Jun 2020 00:58:53.302 * Master replied to PING, replication can continue...
redis-slave-1 | 1:S 06 Jun 2020 00:58:53.306 * Trying a partial resynchronization (request 543ebff4abe27ada53fd7d1f3c0cf1cf55dc0476:659).
redis-slave-1 | 1:S 06 Jun 2020 00:58:53.308 * Successful partial resynchronization with master.
redis-slave-1 | 1:S 06 Jun 2020 00:58:53.308 * MASTER <-> REPLICA sync: Master accepted a Partial Resynchronization.
liumiaocn:redis liumiao$ 

驗證主從

連接確認

因爲上述啓動的環境中,Master在6379提供服務,使用Redis客戶端連接Master

liumiaocn:redis liumiao$ redis-cli -p 6379
127.0.0.1:6379> keys *
(error) NOAUTH Authentication required.
127.0.0.1:6379> 

提示需要進行認證,使用auth命令結合設定的密碼進行認證,並確認當前的keys的狀態

127.0.0.1:6379> auth liumiaocn@server
OK
127.0.0.1:6379> keys *
(empty list or set)
127.0.0.1:6379> 

確認一下slave 1,發現此時信息也爲空

liumiaocn:redis liumiao$ redis-cli -p 6380
127.0.0.1:6380> keys *
(error) NOAUTH Authentication required.
127.0.0.1:6380> auth liumiaocn@slave1
OK
127.0.0.1:6380> keys *
(empty list or set)
127.0.0.1:6380>

設定key

在Master中設定名爲greeting的key,內容設定爲“hello liumiao"

127.0.0.1:6379> set greeting "hello liumiao"
OK
127.0.0.1:6379> keys *
1) "greeting"
127.0.0.1:6379>

確認同步

在Slave節點中確認此key的內容

127.0.0.1:6380> keys *
1) "greeting"
127.0.0.1:6380> get greeting
"hello liumiao"
127.0.0.1:6380> 
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章