docker-compose配置redis哨兵詳細步驟和配置文件
目錄結構調整
redis-cluster/
├── config/
│ ├── master.conf # 主節點配置
│ ├── slave1.conf # 從節點1配置
│ ├── slave2.conf # 從節點2配置
│ ├── sentinel1.conf # 哨兵1配置
│ ├── sentinel2.conf # 哨兵2配置
│ └── sentinel3.conf # 哨兵3配置
└── docker-compose.yml # 包含哨兵的docker-compose配置
Redis配置文件更新
1. config/master.conf
(主節點)
port 6379
bind 0.0.0.0
protected-mode no
logfile "redis-master.log"
dir /data
save 900 1
save 300 10
save 60 10000
requirepass yourpassword
masterauth yourpassword
2. config/slave1.conf
(從節點1)
port 6380
bind 0.0.0.0
protected-mode no
logfile "redis-slave1.log"
dir /data
slaveof redis-master 6379
requirepass yourpassword
masterauth yourpassword
3. config/slave2.conf
(從節點2)
port 6381
bind 0.0.0.0
protected-mode no
logfile "redis-slave2.log"
dir /data
slaveof redis-master 6379
requirepass yourpassword
masterauth yourpassword
哨兵配置文件
4. config/sentinel1.conf
(哨兵1)
port 26379
bind 0.0.0.0
protected-mode no
logfile "sentinel1.log"
dir /data# 監控主節點,mymaster是集群名稱,2是觸發故障轉移所需的最小同意票數
sentinel monitor mymaster redis-master 6379 2# 主節點不可用的判定時間(毫秒)
sentinel down-after-milliseconds mymaster 5000# 故障轉移超時時間(毫秒)
sentinel failover-timeout mymaster 10000# 認證密碼
sentinel auth-pass mymaster yourpassword
5. config/sentinel2.conf
(哨兵2)
port 26379
bind 0.0.0.0
protected-mode no
logfile "sentinel2.log"
dir /data
sentinel monitor mymaster redis-master 6379 2
sentinel down-after-milliseconds mymaster 5000
sentinel failover-timeout mymaster 10000
sentinel auth-pass mymaster yourpassword
6. config/sentinel3.conf
(哨兵3)
port 26379
bind 0.0.0.0
protected-mode no
logfile "sentinel3.log"
dir /data
sentinel monitor mymaster redis-master 6379 2
sentinel down-after-milliseconds mymaster 5000
sentinel failover-timeout mymaster 10000
sentinel auth-pass mymaster yourpassword
更新后的docker-compose.yml
version: '3.8'services:# Redis主節點redis-master:image: redis:7.0container_name: redis-masterports:- "6379:6379"volumes:- ./config/master.conf:/usr/local/etc/redis/redis.conf- redis-data-master:/datacommand: ["redis-server", "/usr/local/etc/redis/redis.conf"]healthcheck:test: ["CMD", "redis-cli", "-a", "yourpassword", "ping"]interval: 5stimeout: 5sretries: 5networks:- redis-network# Redis從節點1redis-slave1:image: redis:7.0container_name: redis-slave1ports:- "6380:6380"volumes:- ./config/slave1.conf:/usr/local/etc/redis/redis.conf- redis-data-slave1:/datacommand: ["redis-server", "/usr/local/etc/redis/redis.conf"]healthcheck:test: ["CMD", "redis-cli", "-a", "yourpassword", "-p", "6380", "ping"]interval: 5stimeout: 5sretries: 5depends_on:- redis-masternetworks:- redis-network# Redis從節點2redis-slave2:image: redis:7.0container_name: redis-slave2ports:- "6381:6381"volumes:- ./config/slave2.conf:/usr/local/etc/redis/redis.conf- redis-data-slave2:/datacommand: ["redis-server", "/usr/local/etc/redis/redis.conf"]healthcheck:test: ["CMD", "redis-cli", "-a", "yourpassword", "-p", "6381", "ping"]interval: 5stimeout: 5sretries: 5depends_on:- redis-masternetworks:- redis-network# 哨兵節點1redis-sentinel1:image: redis:7.0container_name: redis-sentinel1ports:- "26379:26379"volumes:- ./config/sentinel1.conf:/usr/local/etc/redis/sentinel.conf- sentinel-data1:/datacommand: ["redis-sentinel", "/usr/local/etc/redis/sentinel.conf"]healthcheck:test: ["CMD", "redis-cli", "-p", "26379", "ping"]interval: 5stimeout: 5sretries: 5depends_on:- redis-master- redis-slave1- redis-slave2networks:- redis-network# 哨兵節點2redis-sentinel2:image: redis:7.0container_name: redis-sentinel2ports:- "26380:26379"volumes:- ./config/sentinel2.conf:/usr/local/etc/redis/sentinel.conf- sentinel-data2:/datacommand: ["redis-sentinel", "/usr/local/etc/redis/sentinel.conf"]healthcheck:test: ["CMD", "redis-cli", "-p", "26380", "ping"]interval: 5stimeout: 5sretries: 5depends_on:- redis-master- redis-slave1- redis-slave2networks:- redis-network# 哨兵節點3redis-sentinel3:image: redis:7.0container_name: redis-sentinel3ports:- "26381:26379"volumes:- ./config/sentinel3.conf:/usr/local/etc/redis/sentinel.conf- sentinel-data3:/datacommand: ["redis-sentinel", "/usr/local/etc/redis/sentinel.conf"]healthcheck:test: ["CMD", "redis-cli", "-p", "26381", "ping"]interval: 5stimeout: 5sretries: 5depends_on:- redis-master- redis-slave1- redis-slave2networks:- redis-networkvolumes:redis-data-master:redis-data-slave1:redis-data-slave2:sentinel-data1:sentinel-data2:sentinel-data3:networks:redis-network:driver: bridge
部署和驗證步驟
- 創建目錄和配置文件,確保權限正確:
mkdir -p config
chmod -R 644 config/
- 啟動集群:
docker-compose up -d
- 驗證Redis主從狀態:
# 查看主節點信息
docker exec -it redis-master redis-cli -a yourpassword info replication# 查看從節點信息
docker exec -it redis-slave1 redis-cli -a yourpassword -p 6380 info replication
docker exec -it redis-slave2 redis-cli -a yourpassword -p 6381 info replication
- 驗證哨兵狀態:
# 從任一哨兵獲取集群信息
docker exec -it redis-sentinel1 redis-cli -p 26379
127.0.0.1:26379> SENTINEL masters
127.0.0.1:26379> SENTINEL slaves mymaster
測試故障轉移
- 模擬主節點故障:
docker stop redis-master
-
等待約10秒(根據sentinel配置的超時時間),哨兵會自動將一個從節點提升為主節點
-
驗證新的主節點:
# 查看哨兵狀態
docker exec -it redis-sentinel1 redis-cli -p 26379 SENTINEL get-master-addr-by-name mymaster# 確認客戶端可以連接到新主節點
redis-cli -h <new-master-ip> -p 6379 -a yourpassword ping
- 恢復原主節點:
docker start redis-master
原主節點將作為從節點重新加入集群
客戶端連接配置
應用程序應通過哨兵獲取當前主節點地址,而不是直接連接固定節點。例如,使用Redis客戶端連接時:
# Python示例
from redis.sentinel import Sentinelsentinel = Sentinel([('localhost', 26379),('localhost', 26380),('localhost', 26381)
], socket_timeout=0.5)# 獲取主節點連接
master = sentinel.master_for('mymaster', socket_timeout=0.5, password='yourpassword')# 獲取從節點連接(用于讀操作)
slave = sentinel.slave_for('mymaster', socket_timeout=0.5, password='yourpassword')# 執行命令
master.set('foo', 'bar')
value = slave.get('foo')
print(value) # 輸出: b'bar'
這個配置方案實現了一個完整的Redis高可用集群,包含一主二從和三個哨兵節點,可以自動進行故障轉移和恢復。