Redis的常見四種部署方案
這篇文章介紹Reids最為常見的四種部署模式,其實(shí)Reids和數(shù)據(jù)庫的集群模式差不多,可以分為 Redis單機(jī)模式部署、Redis主從模式部署、Redis哨兵模式部署、Cluster集群模式部署,其他的部署方式基本都是圍繞以下幾種方式在進(jìn)行調(diào)整到適應(yīng)的生產(chǎn)環(huán)境,最常見的還是集群模式的部署
接下來我們來主要分析和學(xué)習(xí)一下的部署方式和利弊。
約定信息:
系統(tǒng):Linux CentOS 7.9
Redis版本:Redis 7.2.2
方案一:單機(jī)模式部署 編譯部署
# 設(shè)置內(nèi)核參數(shù) [root@redis ~]# echo "vm.overcommit_memory=1" >> /etc/sysctl.conf [root@redis ~]# echo "net.core.somaxconn=511" >> /etc/sysctl.conf [root@redis ~]# sysctl # 查看生效情況 # 下載二進(jìn)制包并編譯 [root@redis ~]# wget http://download.redis.io/releases/redis-7.2.2.tar.gz [root@redis ~]# tar zxf redis-7.2.2.tar.gz -C /usr/local/ [root@redis ~]# cd /usr/local/redis-7.2.2/ [root@redis redis-7.2.2]# make # 編輯redis.conf配置文件 [root@redis redis-7.2.2]# vim redis.conf # 綁定主機(jī)iP bind 0.0.0.0 # 設(shè)置端口號 port 6379 # 啟用后臺運(yùn)行 daemonize yes # 設(shè)置redis密碼 requirepass 123123 # 啟動并查看監(jiān)聽和進(jìn)程 [root@redis ~]# /usr/local/redis-7.2.2/src/redis-server /usr/local/redis-7.2.2/redis.conf [root@redis ~]# ps -ef | grep redis root 878 1 0 23:24 ? 00:00:00 /sbin/dhclient -q -lf /var/lib/dhclient/dhclient--eth0.lease -pf /var/run/dhclient-eth0.pid -H redis eth0 root 12429 1 0 23:42 ? 00:00:00 /usr/local/redis-7.2.2/src/redis-server 0.0.0.0:6379 root 12505 12289 0 23:43 pts/1 00:00:00 grep --color=auto redis [root@redis ~]# netstat -tnlp | grep redis tcp 0 0 0.0.0.0:6379 0.0.0.0:* LISTEN 12429/redis-server # 停止 [root@redis ~]# ./redis-cli -p 6379 -a 123123 shutdown # 客戶端連接測試測試 [root@redis ~]# /usr/local/redis-7.2.2/src/redis-cli 127.0.0.1:6379> auth 123123 OK 127.0.0.1:6379> set flag if010.com OK 127.0.0.1:6379> get flag "if010.com" 127.0.0.1:6379>
使用systemctl進(jìn)行管理
[root@redis ~]# cp ../utils/redis_init_script /etc/init.d/redis #不同版本可能位置不同 [root@redis ~]# vim /etc/init.d/redis Port : 6379 Config file : /usr/local/redis/conf/redis.conf Log file : /usr/local/redis/log/redis.log Data dir : /usr/local/redis/data Executable : /usr/local/redis/bin/redis-server /usr/local/redis/conf/redis.conf Cli Executable : /usr/local/redis/bin/redis-cli # redis Start up the redis server daemon # # chkconfig: 2345 55 25 添加chkconfig 開機(jī)啟動 .... redis.service [Unit] Description=Redis Server After=network-online.target [Service] Type=forking PIDFile=/var/run/redis_6379.pid ExecStart=/etc/init.d/redis start ExecStop=/etc/init.d/redis stop ExecReload=/etc/init.d/redis reload PrivateTmp=true [Install] WantedBy=multi-user.target
至此單機(jī)模式就部署完成了,優(yōu)點(diǎn)嘛就是能用,缺點(diǎn)就是故障了就無法提供服務(wù),且沒有備份,所以接下來介紹第二種方案—主從模式部署
單點(diǎn)服務(wù)器帶來的問題
- 單點(diǎn)故障,服務(wù)不可用
- 無法處理大量的并發(fā)數(shù)據(jù)
- 數(shù)據(jù)丟失----大災(zāi)難
- 開啟多Redis進(jìn)程
- Redis默認(rèn)單進(jìn)程
- 開啟多進(jìn)程導(dǎo)致CPU壓力過大
- 對于服務(wù)器(縱向)消耗服務(wù)器硬件性能CPU
方案二:主從模式部署 Redis主從原理
和MySQL需要主從復(fù)制的原因一樣,Redis雖然讀取寫入的速度都特別快,但是也會產(chǎn)生性能瓶頸,特別是在讀壓力上,為了分擔(dān)壓力,Redis支持主從復(fù)制。Redis的主從結(jié)構(gòu)一主一從,一主多從或級聯(lián)結(jié)構(gòu),復(fù)制類型可以根據(jù)是否是全量而分為全量同步和增量同步。
下圖為級聯(lián)結(jié)構(gòu):
Redis主從同步的策略
主從同步剛連接的時候進(jìn)行全量同步;全量同步結(jié)束后開始增量同步。如果有需要,slave在任何時候都可以發(fā)起全量同步,其主要策略就是無論如何首先會嘗試進(jìn)行增量同步,如果不成功,則會要求slave進(jìn)行全量同步,之后再進(jìn)行增量同步。
注意:如果多個slave同時斷線需要重啟的時候,因?yàn)橹灰猻lave啟動,就會和master建立連接發(fā)送SYNC請求和主機(jī)全量同步,如果多個同時發(fā)送SYNC請求,可能導(dǎo)致master IO突增而發(fā)送宕機(jī)。
全量同步
Redis全量同步一般發(fā)生在slave的初始階段,這時slave需要將master上的數(shù)據(jù)都復(fù)制一份,具體步驟如下:
- slave連接master,發(fā)送SYNC命令;
- master街道SYNC命令后,執(zhí)行BGSAVE命令生產(chǎn)RDB文件并使用緩沖區(qū)記錄此后執(zhí)行的所有寫命令;
- master的BGSAVE執(zhí)行完成后,向所有的slave發(fā)送快照文件,并在發(fā)送過程中繼續(xù)記錄執(zhí)行的寫命令;
- slave收到快照后,丟棄所有的舊數(shù)據(jù),載入收到的數(shù)據(jù);
- master快照發(fā)送完成后就會開始向slave發(fā)送緩沖區(qū)的寫命令;
- slave完成對快照的載入,并開始接受命令請求,執(zhí)行來自master緩沖區(qū)的寫命令;
- slave完成上面的數(shù)據(jù)初始化后就可以開始接受用戶的讀請求了。
大致流程如下:
增量復(fù)制
增量復(fù)制實(shí)際上就是在slave初始化完成后開始正常工作時master發(fā)生寫操作同步到slave的過程。增量復(fù)制的過程主要是master每執(zhí)行一個寫命令就會向slave發(fā)送相同的寫命令,slave接受并執(zhí)行寫命令,從而保持主從一致。
Redis主從同步的特點(diǎn)
- 采用異步復(fù)制;
- 可以一主多從;
- 主從復(fù)制對于master來說是非阻塞的,也就是說slave在進(jìn)行主從復(fù)制的過程中,master依然可以處理請求;
- 主從復(fù)制對于slave來說也是非阻塞的,也就是說slave在進(jìn)行主從復(fù)制的過程中也可以接受外界的查詢請求,只不過這時候返回的數(shù)據(jù)不一定是正確的。為了避免這種情況發(fā)生,可以在slave的配置文件中配置,在同步過程中阻止查詢;
- 每個slave可以接受來自其他slave的連接;
- 主從復(fù)制提高了Redis服務(wù)的擴(kuò)展性,避免單節(jié)點(diǎn)問題,另外也為數(shù)據(jù)備份冗余提供了一種解決方案;
- 為了降低主redis服務(wù)器寫磁盤壓力帶來的開銷,可以配置讓主redis不在將數(shù)據(jù)持久化到磁盤,而是通過連接讓一個配置的從redis服務(wù)器及時的將相關(guān)數(shù)據(jù)持久化到磁盤,不過這樣會存在一個問題,就是主redis服務(wù)器一旦重啟,因?yàn)橹鱮edis服務(wù)器數(shù)據(jù)為空,這時候通過主從同步可能導(dǎo)致從redis服務(wù)器上的數(shù)據(jù)也被清空;
部署方式
環(huán)境約定:Master節(jié)點(diǎn):172.17.0.100、Slave1節(jié)點(diǎn):172.17.0.101、Slave2節(jié)點(diǎn):172.17.0.102
部署思路:先配置好Master節(jié)點(diǎn),然后拷貝到Slave1節(jié)點(diǎn)上,在Master節(jié)點(diǎn)的配置基礎(chǔ)上再配置replicaof
和masterauth
,其他節(jié)點(diǎn)直接拷貝Slave1節(jié)點(diǎn)上的配置文件即可
編譯安裝
編譯安裝好Redis環(huán)境(所有節(jié)點(diǎn)操作)
# 下載軟件包 [root@Redis-Test1 ~]# wget http://download.redis.io/releases/redis-7.2.2.tar.gz # 解壓軟件包 [root@Redis-Test1 ~]# tar zxf redis-7.2.2.tar.gz -C /usr/local/ [root@Redis-Test1 ~]# cd /usr/local/redis-7.2.2/ [root@Redis-Test1 redis-7.2.2]# ls 00-RELEASENOTES CODE_OF_CONDUCT.md COPYING INSTALL MANIFESTO redis.conf runtest-cluster runtest-sentinel sentinel.conf tests utils BUGS CONTRIBUTING.md deps Makefile README.md runtest runtest-moduleapi SECURITY.md src TLS.md # 編譯 [root@redis-master-01 ~]# make
編輯配置文件
修改Redis的配置文件(Master節(jié)點(diǎn)操作)
[root@Redis-Test1 redis-7.2.2]# vim redis.conf bind 0.0.0.0 port 6379 daemonize yes pidfile /data/redis/redis.pid logfile "/data/redis/logs/redis.log" appendonly yes #開啟AOF持久化 requirepass 123123 dir /data/redis/
修改Redis的配置文件(Slave節(jié)點(diǎn)操作)
[root@Redis-Test2 redis-7.2.2]# vim redis.conf bind 0.0.0.0 port 6379 daemonize yes pidfile /data/redis/redis.pid logfile "/data/redis/logs/redis.log" appendonly yes requirepass 123123 dir /data/redis/ replicaof 172.17.0.100 6379 #指定要同步的master節(jié)點(diǎn)ip和端口 masterauth 123123 #指定master的認(rèn)證口令
啟動
這里要注意一下,先啟動Master節(jié)點(diǎn),然后在啟動Slave節(jié)點(diǎn)
[root@Redis-Test2 redis-7.2.2]# vim redis.conf bind 0.0.0.0 port 6379 daemonize yes pidfile /data/redis/redis.pid logfile "/data/redis/logs/redis.log" appendonly yes requirepass 123123 dir /data/redis/ replicaof 172.17.0.100 6379 #指定要同步的master節(jié)點(diǎn)ip和端口 masterauth 123123 #指定master的認(rèn)證口令
驗(yàn)證主從效果
從日志上分析驗(yàn)證
[root@Redis-Test2 logs]# tailf redis.log 9025:S 01 Nov 2023 17:45:28.450 * Done loading RDB, keys loaded: 0, keys expired: 0. 9025:S 01 Nov 2023 17:45:28.450 * DB loaded from base file appendonly.aof.1.base.rdb: 0.001 seconds 9025:S 01 Nov 2023 17:45:28.450 * DB loaded from append only file: 0.001 seconds 9025:S 01 Nov 2023 17:45:28.450 * Opening AOF incr file appendonly.aof.1.incr.aof on server start 9025:S 01 Nov 2023 17:45:28.450 * Ready to accept connections tcp 9025:S 01 Nov 2023 17:45:28.450 * Connecting to MASTER 172.17.0.100:6379 9025:S 01 Nov 2023 17:45:28.450 * MASTER <-> REPLICA sync started 9025:S 01 Nov 2023 17:45:28.451 * Non blocking connect for SYNC fired the event. 9025:S 01 Nov 2023 17:45:28.451 * Master replied to PING, replication can continue... 9025:S 01 Nov 2023 17:45:28.451 * Partial resynchronization not possible (no cached master) 9025:S 01 Nov 2023 17:45:33.418 * Full resync from master: d9da2499f5cdb878a424e33159ec2b795ea7db17:14 9025:S 01 Nov 2023 17:45:33.419 * MASTER <-> REPLICA sync: receiving streamed RDB from master with EOF to disk 9025:S 01 Nov 2023 17:45:33.419 * MASTER <-> REPLICA sync: Flushing old data 9025:S 01 Nov 2023 17:45:33.419 * MASTER <-> REPLICA sync: Loading DB in memory 9025:S 01 Nov 2023 17:45:33.422 * Loading RDB produced by version 7.2.2 9025:S 01 Nov 2023 17:45:33.422 * RDB age 0 seconds 9025:S 01 Nov 2023 17:45:33.422 * RDB memory usage when created 0.94 Mb 9025:S 01 Nov 2023 17:45:33.422 * Done loading RDB, keys loaded: 0, keys expired: 0. 9025:S 01 Nov 2023 17:45:33.422 * MASTER <-> REPLICA sync: Finished with success 9025:S 01 Nov 2023 17:45:33.422 * Creating AOF incr file temp-appendonly.aof.incr on background rewrite 9025:S 01 Nov 2023 17:45:33.423 * Background append only file rewriting started by pid 9031 9031:C 01 Nov 2023 17:45:33.424 * Successfully created the temporary AOF base file temp-rewriteaof-bg-9031.aof 9031:C 01 Nov 2023 17:45:33.425 * Fork CoW for AOF rewrite: current 4 MB, peak 4 MB, average 4 MB 9025:S 01 Nov 2023 17:45:33.466 * Background AOF rewrite terminated with success 9025:S 01 Nov 2023 17:45:33.466 * Successfully renamed the temporary AOF base file temp-rewriteaof-bg-9031.aof into appendonly.aof.2.base.rdb 9025:S 01 Nov 2023 17:45:33.466 * Successfully renamed the temporary AOF incr file temp-appendonly.aof.incr into appendonly.aof.2.incr.aof 9025:S 01 Nov 2023 17:45:33.469 * Removing the history file appendonly.aof.1.incr.aof in the background 9025:S 01 Nov 2023 17:45:33.469 * Removing the history file appendonly.aof.1.base.rdb in the background 9025:S 01 Nov 2023 17:45:33.472 * Background AOF rewrite finished successfully
從Master節(jié)點(diǎn)上查看節(jié)點(diǎn)信息
[root@Redis-Test1 redis-7.2.2]# ./src/redis-cli 127.0.0.1:6379> auth 123123 OK 127.0.0.1:6379> info replication # Replication role:master connected_slaves:2 slave0:ip=172.17.0.101,port=6379,state=online,offset=98,lag=1 slave1:ip=172.17.0.102,port=6379,state=online,offset=98,lag=1 master_failover_state:no-failover master_replid:d9da2499f5cdb878a424e33159ec2b795ea7db17 master_replid2:0000000000000000000000000000000000000000 master_repl_offset:98 second_repl_offset:-1 repl_backlog_active:1 repl_backlog_size:1048576 repl_backlog_first_byte_offset:1 repl_backlog_histlen:98
方案三:哨兵模式部署
Sentinel是Redis官方為集群提供的高可用解決方案。 在實(shí)際項(xiàng)目中可以使用sentinel去做redis自動故障轉(zhuǎn)移,減少人工介入的工作量,另外sentinel也給客戶端提供了監(jiān)控消息的通知,這樣客戶端就可根據(jù)消息類型去判斷服務(wù)器的狀態(tài),去做對應(yīng)的適配操作
Sentinel 哨兵的作用
- Monitoring(集群監(jiān)控):Sentinel持續(xù)檢查集群中的master、slave狀態(tài),判斷是否存活
- Notification(消息通知):在發(fā)現(xiàn)某個redis實(shí)例死的情況下,Sentinel能通過API通知系統(tǒng)管理員或其他程序腳本
- Automatic failover(故障轉(zhuǎn)移):如果一個master掛掉后,sentinel會啟動故障轉(zhuǎn)移,把某個slave提升為master,其他的slave重新配置指向新master
- Configuration provider(配置中心):對于客戶端來說sentinel通知是有效可信賴的,客戶端會連接sentinel去請求當(dāng)前master的地址,一旦發(fā)生故障sentinel會提供新地址給客戶端
核心功能:在主從復(fù)制的基礎(chǔ)上,哨兵引入了主節(jié)點(diǎn)的自動故障轉(zhuǎn)移
哨兵的核心
- 哨兵至少需要 3 個實(shí)例,來保證自己的健壯性
- 哨兵 + redis 主從的部署架構(gòu),是不保證數(shù)據(jù)零丟失的,只能保證 redis 集群的高可用性
對于哨兵 + redis 主從這種復(fù)雜的部署架構(gòu),盡量在測試環(huán)境和生產(chǎn)環(huán)境,都進(jìn)行充足的測試和演練
哨兵模式的故障遷移
主觀下線
哨兵(Sentinel)節(jié)點(diǎn)會每秒一次的頻率向建立了命令連接的實(shí)例發(fā)送PING命令,如果在down-after-milliseconds毫秒內(nèi)沒有做出有效響應(yīng)包括(PONG/ LOADING/MASTERDOWN)以外的響應(yīng),哨兵就會將該實(shí)例在本結(jié)構(gòu)體中的狀態(tài)標(biāo)記為SRI_s_DOWN主觀下線
客觀下線
當(dāng)一個哨兵節(jié)點(diǎn)發(fā)現(xiàn)主節(jié)點(diǎn)處于主觀下線狀態(tài)是,會向其他的哨兵節(jié)點(diǎn)發(fā)出詢問,該節(jié)點(diǎn)是不是已經(jīng)主觀下線了。如果超過配置參數(shù)quorum個節(jié)點(diǎn)認(rèn)為是主觀下線時,該哨兵節(jié)點(diǎn)就會將自己維護(hù)的結(jié)構(gòu)體中該主節(jié)點(diǎn)標(biāo)記為SRIO DOWN客觀下線詢問命令SENTINEL is-master-down-by-addr
master選舉
在認(rèn)為主節(jié)點(diǎn)客觀下線的情況下,哨兵節(jié)點(diǎn)節(jié)點(diǎn)間會發(fā)起一次選舉,命令為:SENTINEL is-master-down-by-addr只是runid這次會將自己的runid帶進(jìn)去, 希望接受者將自己設(shè)置為主節(jié)點(diǎn)。如果超過半數(shù)以上的節(jié)點(diǎn)返回將該節(jié)點(diǎn)標(biāo)記為leacer的情況下,會有該leader對故障進(jìn)行遷移 master選舉規(guī)則
新主庫選擇:哨兵在選擇新主庫時,先按照一定的篩選條件,把不符合條件的從庫去掉,再按照一定的規(guī)則,給剩下的從庫逐個打分,將得分最高的從庫選為新主庫
從庫篩選
在選主時,除了要檢查從庫的當(dāng)前在線狀態(tài),還要判斷它之前的網(wǎng)絡(luò)連接狀態(tài),如果從庫總是和主庫斷連,而且斷連次數(shù)超出了一定的閾值,表明這個從庫的網(wǎng)絡(luò)狀況并不是太好,就可以把這個從庫去掉了
在sentinel配置項(xiàng)down-after-milliseconds * 10
中,down-after-milliseconds 是認(rèn)定主從庫斷連的最大連接超時時間,如果在down-aftermilliseconds毫秒內(nèi),主從節(jié)點(diǎn)都沒有通過網(wǎng)絡(luò)聯(lián)系上,就可以認(rèn)為主從節(jié)點(diǎn)斷連了,如果發(fā)生斷連的次數(shù)超過了10次,就說明這個從庫的網(wǎng)絡(luò)狀況不好,不適合作為新主庫
從庫分?jǐn)?shù)判斷
Sentinle集群選主中,分別按照三個規(guī)則依次進(jìn)行三輪打分,這三個規(guī)則分別是從庫優(yōu)先級、從庫復(fù)制進(jìn)度以及從庫 ID 號,只要在某一輪中,有從庫得分最高,那么它就是主庫了,選主過程到此結(jié)束,如果沒有出現(xiàn)得分最高的從庫,那么就繼續(xù)進(jìn)行下一輪
第一輪:優(yōu)先級最高的從庫得分高
用戶可以通過slave-priority配置項(xiàng),給不同的從庫設(shè)置不同優(yōu)先級,比如,有兩個從庫,它們的內(nèi)存大小不一樣,可以手動給內(nèi)存大的實(shí)例設(shè)置一個高優(yōu)先級,在選主時, 哨兵會給優(yōu)先級高的從庫打高分,如果有一個從庫優(yōu)先級最高,那么它就是新主庫了,如果從庫的優(yōu)先級都一樣,那么哨兵開始第二輪打分
第二輪:和舊主庫同步程度最接近的從庫得分高
這個規(guī)則的依據(jù)是,如果選擇和舊主庫同步最接近的那個從庫作為主庫,那么,這個新主庫上就有最新的數(shù)據(jù)
如何判斷從庫和舊主庫間的同步進(jìn)度呢?
主從庫同步時有個命令傳播的過程。在這個過程中,主庫會用master_repl_offset
記錄當(dāng)前的最新寫操作在 repl_backlog_buffer
中的位置,而從庫會用slave_repl_offset
這個值記錄當(dāng)前的復(fù)制進(jìn)度
此時,我們想要找的從庫,它的slave_repl_offset
需要最接近master_repl_offset
,如果在所有從庫中,有從庫的slave_repl_offset
最接近master_repl_offset
,那么它的得分就最高,可以作為新主庫,但并不是取slave_repl_offset
與master_repl_offset
做對比,而是不同從庫的slave_repl_offset
進(jìn)行對比的,因?yàn)檫@個時候master已經(jīng)掛掉了,無法獲取master_repl_offset
,所以在實(shí)際的選主代碼中,哨兵在這一步,是通過比較不同從庫的slave_repl_offset
,找出最大slave_repl_offset
的從庫,也就是選擇salve_repl_offset
最大的那個從庫
master_repl_offset機(jī)制:master_repl_offset是單調(diào)增加的,它的值可以大于repl_backlog_size。Redis會用一個名為repl_backlog_idx的值記錄在環(huán)形緩沖區(qū)中的最新寫入位置
舉個例子,例如寫入len的數(shù)據(jù),那么 master_repl_offset += len > repl_backlog_idx += len,但是,如果repl_backlog_idx等于repl_backlog_size時,repl_backlog_idx會被置為0,表示從環(huán)形緩沖區(qū)開始位置繼續(xù)寫入
第三輪:ID 號小的從庫得分高
每個實(shí)例都會有一個 ID,這個 ID 就類似于這里的從庫的編號,目前Redis在選主庫時,有一個默認(rèn)的規(guī)定:在優(yōu)先級和復(fù)制進(jìn)度都相同的情況下,ID 號最小的從庫得分最高,會被選為新主庫,Redis server啟動時,會生成一個40字節(jié)長的隨機(jī)字符串作為runID,具體算法用的是 SHA-1算法
部署方式
環(huán)境約定:Master節(jié)點(diǎn):172.17.0.100、Slave1節(jié)點(diǎn):172.17.0.101、Slave2節(jié)點(diǎn):172.17.0.102
部署思路:先配置好主從模式的環(huán)境,然后再修改sentinel.conf
配置文件,最后啟動即可
編譯安裝
編譯安裝好Redis環(huán)境(所有節(jié)點(diǎn)操作)
# 下載軟件包 [root@Redis-Test1 ~]# wget http://download.redis.io/releases/redis-7.2.2.tar.gz # 解壓軟件包 [root@Redis-Test1 ~]# tar zxf redis-7.2.2.tar.gz -C /usr/local/ [root@Redis-Test1 ~]# cd /usr/local/redis-7.2.2/ [root@Redis-Test1 redis-7.2.2]# ls 00-RELEASENOTES CODE_OF_CONDUCT.md COPYING INSTALL MANIFESTO redis.conf runtest-cluster runtest-sentinel sentinel.conf tests utils BUGS CONTRIBUTING.md deps Makefile README.md runtest runtest-moduleapi SECURITY.md src TLS.md # 編譯 [root@redis-master-01 ~]# make
編輯redis配置文件
修改Redis的配置文件(Master節(jié)點(diǎn)操作)
[root@Redis-Test1 redis-7.2.2]# vim redis.conf bind 0.0.0.0 port 6379 daemonize yes pidfile /data/redis/redis.pid logfile "/data/redis/logs/redis.log" appendonly yes #開啟AOF持久化 requirepass 123123 dir /data/redis/
修改Redis的配置文件(Slave節(jié)點(diǎn)操作)
[root@Redis-Test2 redis-7.2.2]# vim redis.conf bind 0.0.0.0 port 6379 daemonize yes pidfile /data/redis/redis.pid logfile "/data/redis/logs/redis.log" appendonly yes requirepass 123123 dir /data/redis/ replicaof 172.17.0.100 6379 #指定要同步的master節(jié)點(diǎn)ip和端口 masterauth 123123 #指定master的認(rèn)證口令
啟動Redis服務(wù)
這里要注意一下,先啟動Master節(jié)點(diǎn),然后在啟動Slave節(jié)點(diǎn)
/usr/local/redis-7.2.2/src/redis-server /usr/local/redis-7.2.2/redis.conf
到此結(jié)束主從環(huán)境的配置,接下來配置哨兵環(huán)節(jié)
配置Sentinel配置文件
修改Redis哨兵模式的配置文件(所有節(jié)點(diǎn)操作)
[root@Redis-Test1 redis-7.2.2]# vim sentinel.conf bind 0.0.0.0 port 26379 daemonize yes #哨兵的啟動模式,yes是后臺啟動 pidfile /data/redis/redis-sentinel.pid #哨兵的pid文件存放位置 logfile "/data/redis/logs/redis-sentinel.log" #哨兵的日志文件存放位置 dir /data #哨兵進(jìn)程的工作目錄,默認(rèn)就是/tmp #哨兵監(jiān)聽的master數(shù)據(jù)庫,mymaster是為主數(shù)據(jù)庫起的名稱,可以隨便起個名字,后面是master的ip和端口 # 最后面的1表示選舉個數(shù),含義是需要多少個哨兵認(rèn)為master掛了才認(rèn)定master掛掉,這里我設(shè)置為1是因?yàn)槲抑挥幸粋€哨兵,如果你配置了多個哨兵,建議配置2以上數(shù)字。 sentinel monitor mymaster 172.17.0.100 6379 1 sentinel auth-pass mymaster 123123 #配置master的登陸密碼,mymaster是你配置的master名稱 sentinel down-after-milliseconds mymaster 30000 #30秒內(nèi)master無響應(yīng)則認(rèn)為master掛掉 acllog-max-len 128 #保持默認(rèn)即可 #master重新選舉之后,其它節(jié)點(diǎn)能同時并行進(jìn)行數(shù)據(jù)同步的臺數(shù)有多少臺 #顯然該值越大,則所有slave能同步完成的速度越快,但如果此時剛好有人訪問slave數(shù)據(jù),可能造成讀取失敗,最保守的值建議設(shè)為1 #即同一時間只能有一臺進(jìn)行數(shù)據(jù)同步,這樣其它slave還能繼續(xù)提供服務(wù),但是所有的slave數(shù)據(jù)同步完成就會顯得緩慢。 sentinel parallel-syncs mymaster 1 sentinel failover-timeout mymaster 180000 #故障轉(zhuǎn)移超時時間,指在該時間內(nèi)如果故障轉(zhuǎn)移沒有成功,則會再發(fā)起一次故障轉(zhuǎn)移 sentinel deny-scripts-reconfig yes #保持默認(rèn)即可 SENTINEL resolve-hostnames no #保持默認(rèn)即可 SENTINEL announce-hostnames no #保持默認(rèn)即可
啟動哨兵服務(wù)
先啟master的哨兵,再啟slave的哨兵
/usr/local/redis-7.2.2/src/redis-sentinel /usr/local/redis-7.2.2/sentinel.conf
查看相關(guān)信息
[root@Redis-Test3 redis-7.2.2]# ./src/redis-cli -p 26379 127.0.0.1:26379> info sentinel # Sentinel sentinel_masters:1 sentinel_tilt:0 sentinel_tilt_since_seconds:-1 sentinel_running_scripts:0 sentinel_scripts_queue_length:0 sentinel_simulate_failure_flags:0 master0:name=mymaster,status=ok,address=172.17.0.100:6379,slaves=2,sentinels=1
驗(yàn)證故障轉(zhuǎn)移
關(guān)閉Master節(jié)點(diǎn),觀察日志和sentinel信息
12697:X 01 Nov 2023 19:45:57.990 # +monitor master mymaster 172.17.0.100 6379 quorum 1 12697:X 01 Nov 2023 19:47:10.430 # +sdown master mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:10.430 # +odown master mymaster 172.17.0.100 6379 #quorum 1/1 12697:X 01 Nov 2023 19:47:10.430 # +new-epoch 1 12697:X 01 Nov 2023 19:47:10.430 # +try-failover master mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:10.434 * Sentinel new configuration saved on disk 12697:X 01 Nov 2023 19:47:10.434 # +vote-for-leader 02f863db4ebd9962c4557bcad9ec78afd2b86613 1 12697:X 01 Nov 2023 19:47:10.434 # +elected-leader master mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:10.434 # +failover-state-select-slave master mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:10.517 # +selected-slave slave 172.17.0.102:6379 172.17.0.102 6379 @ mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:10.517 * +failover-state-send-slaveof-noone slave 172.17.0.102:6379 172.17.0.102 6379 @ mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:10.690 * +failover-state-wait-promotion slave 172.17.0.102:6379 172.17.0.102 6379 @ mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:11.607 * Sentinel new configuration saved on disk 12697:X 01 Nov 2023 19:47:11.607 # +promoted-slave slave 172.17.0.102:6379 172.17.0.102 6379 @ mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:11.607 # +failover-state-reconf-slaves master mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:11.703 * +slave-reconf-sent slave 172.17.0.101:6379 172.17.0.101 6379 @ mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:12.814 * +slave-reconf-inprog slave 172.17.0.101:6379 172.17.0.101 6379 @ mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:12.814 * +slave-reconf-done slave 172.17.0.101:6379 172.17.0.101 6379 @ mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:12.866 # +failover-end master mymaster 172.17.0.100 6379 12697:X 01 Nov 2023 19:47:12.866 # +switch-master mymaster 172.17.0.100 6379 172.17.0.102 6379 12697:X 01 Nov 2023 19:47:12.867 * +slave slave 172.17.0.101:6379 172.17.0.101 6379 @ mymaster 172.17.0.102 6379 12697:X 01 Nov 2023 19:47:12.867 * +slave slave 172.17.0.100:6379 172.17.0.100 6379 @ mymaster 172.17.0.102 6379 12697:X 01 Nov 2023 19:47:12.871 * Sentinel new configuration saved on disk 12697:X 01 Nov 2023 19:47:42.911 # +sdown slave 172.17.0.100:6379 172.17.0.100 6379 @ mymaster 172.17.0.102 6379
[root@Redis-Test3 redis-7.2.2]# ./src/redis-cli -p 26379 127.0.0.1:26379> info sentinel # Sentinel sentinel_masters:1 sentinel_tilt:0 sentinel_tilt_since_seconds:-1 sentinel_running_scripts:0 sentinel_scripts_queue_length:0 sentinel_simulate_failure_flags:0 master0:name=mymaster,status=ok,address=172.17.0.102:6379,slaves=2,sentinels=1 [root@Redis-Test3 redis-7.2.2]# ./src/redis-cli 127.0.0.1:6379> info replication # Replication role:master connected_slaves:1 slave0:ip=172.17.0.101,port=6379,state=online,offset=55358,lag=0 master_failover_state:no-failover master_replid:1bc5d3796192e6c518baa423a3d24573a0360abd master_replid2:0963bdef90dddf0294c0972160a9476e40345768 master_repl_offset:55358 second_repl_offset:8434 repl_backlog_active:1 repl_backlog_size:1048576 repl_backlog_first_byte_offset:1 repl_backlog_histlen:55358
關(guān)于切換不成功常見的問題
無法切換,有幾種情況:
- redis保護(hù)模式開啟了
- 選舉個數(shù)多了或者少了
- 端口沒有放開
- master密碼和從密碼不一致
- master節(jié)點(diǎn)的redis.conf沒有添加masterauth
方案四:集群模式部署
集群,即Redis Cluster,是Redis 3.0開始引入的分布式存儲方案,集群由多個節(jié)點(diǎn)(Node)組成,Redis的數(shù)據(jù)分布在這些節(jié)點(diǎn)中,集群中的節(jié)點(diǎn)分為主節(jié)點(diǎn)和從節(jié)點(diǎn):只有主節(jié)點(diǎn)負(fù)責(zé)讀寫請求和集群信息的維護(hù),從節(jié)點(diǎn)只進(jìn)行主節(jié)點(diǎn)數(shù)據(jù)和狀態(tài)信息的復(fù)制
Redis-Cluster集群的作用
數(shù)據(jù)分區(qū): 數(shù)據(jù)分區(qū)(或稱數(shù)據(jù)分片)是集群最核心的功能,集群將數(shù)據(jù)分散到多個節(jié)點(diǎn),一方面突破了Redis單機(jī)內(nèi)存大小的限制,存儲容量大大增加,另一方面每個主節(jié)點(diǎn)都可以對外提供讀服務(wù)和寫服務(wù),大大提高了集群的響應(yīng)能力,Redis單機(jī)內(nèi)存大小受限問題,在介紹持久化和主從復(fù)制時都有提及,例如,如果單機(jī)內(nèi)存太大,bgsave和bgrewriteaof 的保存操作可能導(dǎo)致主進(jìn)程阻塞,主從環(huán)境下主機(jī)切換時可能導(dǎo)致從節(jié)點(diǎn)長時間無法提供服務(wù),全量復(fù)制階段主節(jié)點(diǎn)的復(fù)制緩沖區(qū)可能溢出
高可用: 集群支持主從復(fù)制和主節(jié)點(diǎn)的自動故障轉(zhuǎn)移(與哨兵類似)當(dāng)任一節(jié)點(diǎn)發(fā)生故障時,集群仍然可以對外提供服務(wù) Redis集群的數(shù)據(jù)分片
Redis集群引入了哈希槽的概念,Redis集群有16384個哈希槽(編號0-16383)集群的每個節(jié)點(diǎn)負(fù)責(zé)部分哈希槽,每個Key通過CRc16校驗(yàn)后對16384取余來決定放置哪個哈希槽,通過這個值,去找到對應(yīng)的插槽所對應(yīng)的節(jié)點(diǎn),然后直接自動跳轉(zhuǎn)到這個對應(yīng)的節(jié)點(diǎn)上進(jìn)行存取操作
以3個節(jié)點(diǎn)組成的集群為例:
節(jié)點(diǎn)A包含0到5460號哈希槽
節(jié)點(diǎn)B包含5461到10922號哈希槽
節(jié)點(diǎn)C包含10923到16383號哈希槽
Redis集群的主從復(fù)制模型
集群中具有A、B、C三個節(jié)點(diǎn),如果節(jié)點(diǎn)B失敗了,整個集群就會因缺少5461-10922這個范圍的槽而不可以用,為每個節(jié)點(diǎn)添加一個從節(jié)點(diǎn)A1、B1、C1整個集群便有三個Master節(jié)點(diǎn)和三個slave 節(jié)點(diǎn)組成,在節(jié)點(diǎn)B失敗后,集群選舉一位為主節(jié)點(diǎn)繼續(xù)服務(wù),但是要注意的是當(dāng)B和B1都失敗后,集群將不可用
Redis Cluster的工作原理
在哨兵sentinel機(jī)制中,可以解決redis高可用問題,即當(dāng)master故障后可以自動將slave提升為master,從而可以保證redis服務(wù)的正常使用,但是無法解決redis單機(jī)寫入的瓶頸問題,即單機(jī)redis寫入性能受限于單機(jī)的內(nèi)存大小、并發(fā)數(shù)量、網(wǎng)卡速率等因素
部署方式
環(huán)境約定:
- Master節(jié)點(diǎn):172.17.0.101、172.17.0.103、172.17.0.105
- Slave節(jié)點(diǎn):172.17.0.102、172.17.0.104、172.17.0.106
部署思路:安裝部署好所有節(jié)點(diǎn)的redis服務(wù)并啟動,然后使用自動部署集群工具設(shè)定集群
編譯安裝
# 下載軟件包 [root@redis-master-01 ~]# wget http://download.redis.io/releases/redis-7.2.2.tar.gz # 解壓軟件包 [root@redis-master-01 ~]# tar zxf redis-7.2.2.tar.gz -C /usr/local/ [root@redis-master-01 ~]# cd /usr/local/redis-7.2.2/ [root@redis-master-01 redis-7.2.2]# ls 00-RELEASENOTES CODE_OF_CONDUCT.md COPYING INSTALL MANIFESTO redis.conf runtest-cluster runtest-sentinel sentinel.conf tests utils BUGS CONTRIBUTING.md deps Makefile README.md runtest runtest-moduleapi SECURITY.md src TLS.md # 編譯 [root@redis-master-01 ~]# make
編輯配置文件
# 編輯配置文件 vim /usr/local/redis-7.2.2/redis.conf # 監(jiān)聽端口 port 6379 # IP不限制,習(xí)慣改成0了,必須,避免后面出現(xiàn)麻煩,如果是外網(wǎng),必須! bind 0.0.0.0 # 設(shè)置Redis實(shí)例pid文件 pidfile /data/redis/redis.pid # 后臺模式,必須 daemonize yes # 僅追加 appendonly yes appendfsync always # 集群開啟,必須 cluster-enabled yes # 節(jié)點(diǎn)信息,可選,因?yàn)橄到y(tǒng)會默認(rèn) cluster-config-file nodes.conf # 設(shè)置當(dāng)前節(jié)點(diǎn)連接超時毫秒數(shù) cluster-node-timeout 15000 # 數(shù)據(jù)存放目錄 dir /data/redis/ # 認(rèn)證密碼 requirepass 123123 # 設(shè)置客戶端連接時的超時時間,單位為秒 timeout 60 # 日志等級:debug,revbose,notice和warning loglevel notice # 配置log文件地址,默認(rèn)使用標(biāo)準(zhǔn)輸出 logfile "/data/redis/logs/redis.log" # 設(shè)置數(shù)據(jù)庫的個數(shù),默認(rèn)使用的數(shù)據(jù)庫是0 databases 16 # 設(shè)置redis進(jìn)行數(shù)據(jù)庫鏡像的頻率 save 900 1 300 10 60 10000 # 鏡像備份文件的文件名 dbfilename dump.rdb
啟動Redis
# 啟動Redis [root@redis-master-01 redis-7.2.2]# /usr/local/redis-7.2.2/src/redis-server /usr/local/redis-7.2.2/redis.conf [root@redis-master-01 ~]# netstat -tnlp Active Internet connections (only servers) Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN 1083/sshd tcp 0 0 0.0.0.0:16379 0.0.0.0:* LISTEN 10980/redis-server tcp 0 0 0.0.0.0:6379 0.0.0.0:* LISTEN 10980/redis-server
驗(yàn)證服務(wù)
驗(yàn)證沒有問題后其余的節(jié)點(diǎn)也是這么配置即可~
自動搭建集群
Redis 3.0 版本之后官方發(fā)布了一個集群管理工具 redis-trib.rb,集成在 Redis 源碼包的src目錄下。其封裝了 Redis 提供的集群命令,使用簡單、便捷。不過 redis-trib.rb 是 Redis 作者使用 Ruby 語言開發(fā)的,故使用該工具之前還需要先在機(jī)器上安裝 Ruby 環(huán)境。后面作者可能意識到這個問題,Redis 5.0 版本開始便把這個工具集成到 redis-cli 中,以–cluster參數(shù)提供使用,其中create命令可以用來創(chuàng)建集群。如果您安裝的 Redis 是 3.x 和 4.x 的版本可以使用 redis-trib.rb 搭建,不過之前需要安裝 Ruby 環(huán)境。先使用 yum 安裝 Ruby 環(huán)境以及其他依賴項(xiàng):
yum -y install ruby ruby-devel rubygems rpm-build
查看ruby版本
ruby -v
確認(rèn)沒有問題之后,我們就可以創(chuàng)建集群了
./redis-cli -a 123123 --cluster create 172.17.0.101:6379 172.17.0.103:6379 172.17.0.105:6379 172.17.0.102:6379 172.17.0.104:6379 172.17.0.106:6379 --cluster-replicas 1
注意:主節(jié)點(diǎn)在前,從節(jié)點(diǎn)在后。其中–cluster-replicas參數(shù)用來指定一個主節(jié)點(diǎn)帶有的從節(jié)點(diǎn)個數(shù),如上–cluster-replicas 1即表示 1 個主節(jié)點(diǎn)有 1 個從節(jié)點(diǎn)
至此,Redis集群搭建完畢!
我們可以查看一下節(jié)點(diǎn)信息,用一下命令或者可查看redis任意一個目錄下的 nodes.conf
配置文件
[root@redis-master-01 ~]# cat /data/redis/nodes.conf 5f2ce841ecf51d58be0120f7132e1abff2f3b8bc 172.17.0.102:6379@16379,,tls-port=0,shard-id=327de171b1a685bf6f4741253bb8dc7c3134b7b4 slave 78f722a1b410336219fafbe1813fdb5456d9cf0a 0 1698661133000 3 connected 25115e9cb55c0981f16165f19ade5b9de5c6ce87 172.17.0.103:6379@16379,,tls-port=0,shard-id=19c2b46d9a0d0038ae1b57f6c7c4449eb6647c6f master - 0 1698661133000 2 connected 5461-10922 f7cf16beffbb991aa1a2de43b6738289904d683b 172.17.0.104:6379@16379,,tls-port=0,shard-id=8d019b1cdda30d0ad959a197c7cf6308016d1999 slave 278629f1ab3f5d1fcfdbb1274d3000d03be102a7 0 1698661131000 1 connected 2ab90783a1275af9e1fbcee0d3207bea36953e89 172.17.0.106:6379@16379,,tls-port=0,shard-id=19c2b46d9a0d0038ae1b57f6c7c4449eb6647c6f slave 25115e9cb55c0981f16165f19ade5b9de5c6ce87 1698661126915 1698661124000 2 disconnected 278629f1ab3f5d1fcfdbb1274d3000d03be102a7 172.17.0.101:6379@16379,,tls-port=0,shard-id=8d019b1cdda30d0ad959a197c7cf6308016d1999 myself,master - 0 1698661124000 1 connected 0-5460 78f722a1b410336219fafbe1813fdb5456d9cf0a 172.17.0.105:6379@16379,,tls-port=0,shard-id=327de171b1a685bf6f4741253bb8dc7c3134b7b4 master - 0 1698661133000 3 connected 10923-16383 vars currentEpoch 6 lastVoteEpoch 0
或者
[root@redis-master-01 ~]# cat /data/redis/nodes.conf 5f2ce841ecf51d58be0120f7132e1abff2f3b8bc 172.17.0.102:6379@16379,,tls-port=0,shard-id=327de171b1a685bf6f4741253bb8dc7c3134b7b4 slave 78f722a1b410336219fafbe1813fdb5456d9cf0a 0 1698661133000 3 connected 25115e9cb55c0981f16165f19ade5b9de5c6ce87 172.17.0.103:6379@16379,,tls-port=0,shard-id=19c2b46d9a0d0038ae1b57f6c7c4449eb6647c6f master - 0 1698661133000 2 connected 5461-10922 f7cf16beffbb991aa1a2de43b6738289904d683b 172.17.0.104:6379@16379,,tls-port=0,shard-id=8d019b1cdda30d0ad959a197c7cf6308016d1999 slave 278629f1ab3f5d1fcfdbb1274d3000d03be102a7 0 1698661131000 1 connected 2ab90783a1275af9e1fbcee0d3207bea36953e89 172.17.0.106:6379@16379,,tls-port=0,shard-id=19c2b46d9a0d0038ae1b57f6c7c4449eb6647c6f slave 25115e9cb55c0981f16165f19ade5b9de5c6ce87 1698661126915 1698661124000 2 disconnected 278629f1ab3f5d1fcfdbb1274d3000d03be102a7 172.17.0.101:6379@16379,,tls-port=0,shard-id=8d019b1cdda30d0ad959a197c7cf6308016d1999 myself,master - 0 1698661124000 1 connected 0-5460 78f722a1b410336219fafbe1813fdb5456d9cf0a 172.17.0.105:6379@16379,,tls-port=0,shard-id=327de171b1a685bf6f4741253bb8dc7c3134b7b4 master - 0 1698661133000 3 connected 10923-16383 vars currentEpoch 6 lastVoteEpoch 0
注意:
鏈接時候,務(wù)必選擇集群模式鏈接(如果你鏈接失敗,可以重新看上面配置文件部分,或者往下看)
由于自動生成的nodes.conf文件里面,會默認(rèn)生成帶有內(nèi)網(wǎng)IP,所以你如果是要使用外網(wǎng)鏈接,就去把每一個Redis目錄下的
/data/redis/nodes.conf
配置文件里面IP為內(nèi)網(wǎng)的改成外網(wǎng),并且16379端口也要被允許訪問(注意防火墻問題),然后再重啟所有Redis!不用再重新創(chuàng)建集群!
附錄:Redis配置參數(shù)介紹
基礎(chǔ)配置
bind
默認(rèn)配置:bind 127.0.0.1
,如果沒用通過bind命令明確綁定ip,redis可以監(jiān)聽到請求過來的所有網(wǎng)絡(luò)接口,
bind后面拼接1個或多個ip地址,那么該redis實(shí)例只能監(jiān)聽到來自這幾個ip的請求,
# 舉例 bind 192.168.1.100 10.0.0.1 bind 127.0.0.1 ::1 # redis默認(rèn)配置的是只允許本機(jī)訪問:bind 127.0.0.1 # 如果需要redis允許其他ip訪問,那么注釋掉默認(rèn)配置即可:#bind 127.0.0.1
port
默認(rèn)配置:port 6379
,port用來配置redis接受連接的端口,即監(jiān)聽端口
protected-mode
默認(rèn)配置:protected-mode yes
,protected mode是一個安全保護(hù)層,用來避免redis實(shí)例暴漏在互聯(lián)網(wǎng)被訪問或者利用,如果開啟保護(hù)模式并且沒有通過bind綁定外部的ip地址并且沒有通過requirepass配置密碼,那么該redis實(shí)例只能接受本地127.0.0.1回環(huán)地址的連接,如果想運(yùn)行其他主機(jī)訪問,那么可以將保護(hù)模式關(guān)閉:protected-mode no
daemonize
默認(rèn)配置:daemonize no
,redis默認(rèn)不是以守護(hù)進(jìn)程的方式后臺運(yùn)行,如果想后臺運(yùn)行,開啟配置:daemonize yes
supervised
默認(rèn)配置:supervised no
,是否Supervised模式運(yùn)行Redis
pidfile
默認(rèn)值:pidfile /var/run/redis_6379.pid
,如果配置指定了pid 文件,Redis就用該配置的pid文件寫入,退出的時候移除對應(yīng)的pid文件。如果Redis是以非守護(hù)進(jìn)程模式的運(yùn)行,又沒有配置指定的pid文件,那么不會創(chuàng)建pid文件。如果Redis是守護(hù)進(jìn)程的模式,即使沒有配置指定的pid文件,會默認(rèn)使用 /var/run/redis.pid
文件
loglevel
默認(rèn)配置:loglevel notice
,指定Server的日志級別,有以下四種級別:
- debug(包含許多具體信息,開發(fā)/測試環(huán)境下很方便)
- verbose(包含許多不常用的信息,但沒有debug級別那么混亂)
- notice(適中的信息,很適合生產(chǎn)環(huán)境)
- warning(只記錄重要或者非常的信息)
logfile
默認(rèn)值:logfile “”
,指定log文件名。配置成空串的話可以強(qiáng)制Redis在標(biāo)準(zhǔn)輸出記錄日志。如果使用標(biāo)準(zhǔn)輸出進(jìn)行日志記錄且是以守護(hù)進(jìn)程的模式運(yùn)行,日志會在/dev/null
中。
syslog-enabled
默認(rèn)配置:syslog-enabled no
,想讓日志記錄到系統(tǒng)日志,設(shè)置syslog-enabled成yes
syslog-ident
默認(rèn)配置:syslog-ident redis
,指定syslog的身份
syslog-facility
默認(rèn)配置:syslog-facility local0
,指定syslog工具(facility),一定要是USER或者在LOCAL0 - LOCAL7
之間
databases
默認(rèn)配置:databases 16
,設(shè)置數(shù)據(jù)庫的數(shù)量。默認(rèn)的數(shù)據(jù)庫號是DB 0
always-show-logo
默認(rèn)配置:always-show-logo yes
,Redis會在啟動的時候,如果標(biāo)準(zhǔn)輸出日志是TTY,則會在開始記錄標(biāo)準(zhǔn)輸出日志的時候展示一個ASCII字符組成的Redis Logo,也就是說,通常只在交互的會話中會展示該Logo
持久化配置配置 RDB
save
默認(rèn)配置:save 900 1 300 10 60 10000
,rdb保存數(shù)據(jù),如果時間秒數(shù)seconds和寫的次數(shù)都配置了,那么一旦達(dá)到了配置條件Redis會將DB保存到硬盤
以默認(rèn)配置舉例,達(dá)到了以下條件會觸發(fā)寫磁盤:
900秒內(nèi)(15分鐘)且數(shù)據(jù)庫中至少有1個key被改變。
300秒內(nèi)(5分鐘)且數(shù)據(jù)庫中至少有10個key被改變。
60秒內(nèi)(1分鐘)且數(shù)據(jù)庫中只有一個10000個key被改變。
可以通過添加一個帶空串的save指令來讓配置的save選擇失效,比如:save ""
stop-writes-on-bgsave-error
默認(rèn)配置:stop-writes-on-bgsave-error yes
,在開啟了RDB快照后,如果最近的一次RDB快照在后臺生成失敗的話,Redis默認(rèn)會拒絕所有的寫請求。這么做的目的是為了讓用戶注意到后臺持久化可能出現(xiàn)了問題。否則用戶可能一直無法注意到問題,進(jìn)而可能導(dǎo)致災(zāi)難級別的事情發(fā)生。如果bgsave正常,Redis會自動的繼續(xù)處理寫請求。如果已經(jīng)為Redis實(shí)例和持久化配置了合適的監(jiān)控手段,且希望Redis在非理想情況下(比如硬盤問題,權(quán)限問題等等)仍繼續(xù)提供服務(wù),可以將此項(xiàng)配置為no
rdbcompression
默認(rèn)配置:rdbcompression yes
,想要在生成rdb文件的時候使用LZF壓縮String對象,將該配置保持默認(rèn)為yes幾乎不會出現(xiàn)意外狀況,可以將該配置設(shè)置為no來節(jié)省CPU開銷,但是那些原本可以被壓縮的key和value會讓數(shù)據(jù)集更大
dbchecksum
默認(rèn)配置:rdbchecksum yes
,從5.0版本開始RDB文件的末尾會默認(rèn)放置一個CRC64的校驗(yàn)碼,這會讓文件的格式更加容易檢驗(yàn)驗(yàn)證,代價是生成和加載RDB文件的性能會損失10%左右,你可以把該配置關(guān)閉以求更佳的性能,沒有開啟校驗(yàn)碼配置的RDB文件會將校驗(yàn)碼設(shè)置為0,加載該文件的程序就會跳過校驗(yàn)過程
dbfilename
默認(rèn)配置:dbfilename dump.rdb
,配置rdb文件的名稱
dir
默認(rèn)配置:dir ./
,工作目錄,存儲rdb文件的目錄,數(shù)據(jù)庫會使用該配置放置rdb文件,文件的名字使用上面的dbfilename指定的文件名,AOF文件的存儲位置也會使用這個配置項(xiàng),但要注意是配置一個目錄而不是文件名
AOF
appendonly
Redis默認(rèn)使用異步方式轉(zhuǎn)儲數(shù)據(jù)到硬盤,但在Redis處理出現(xiàn)問題或者設(shè)備斷電的意外期間可能丟失相應(yīng)的寫操作(取決于save配置的時間點(diǎn)),AOF文件是Redis提供的另外一種提供更好的持久性的持久化模式,例如如果使用默認(rèn)的數(shù)據(jù)傳輸策略(根據(jù)之后提供的配置)Redis在發(fā)生意外情況下比如設(shè)備斷電,或者Redis本身的進(jìn)程出現(xiàn)了一些問題的情況下(操作系統(tǒng)正常運(yùn)行),Redis可以僅僅丟失1秒鐘的寫操作,AOF和RDB的持久化策略可以同時啟用,如果打開了AOF,Redis啟動時會加載AOF
常見配置: appendonly yes #開啟AOF appendfilename "appendonly.aof" #AOF 的文件名
appendfsync
默認(rèn)配置:appendfsync everysec
,函數(shù)fsync()會告訴操作系統(tǒng)立即把數(shù)據(jù)寫到磁盤上而不是等輸出緩沖區(qū)有更多的數(shù)據(jù)時才進(jìn)行,有些OS會馬上把數(shù)據(jù)刷到硬盤,有些OS只保證盡快進(jìn)行刷盤操作
Redis 支持三種模式:
- no:不fsync,讓操作系統(tǒng)來決定什么時候進(jìn)行刷盤,最不會影響Server響應(yīng)
- always:每寫入aof文件就進(jìn)行fsync,影響Server響應(yīng),但是數(shù)據(jù)更安全
- everysec:默認(rèn)模式,每秒進(jìn)行fsync,最穩(wěn)健的形式,在響應(yīng)速度和數(shù)據(jù)安全方面最穩(wěn)妥的選擇,選擇no,讓OS選擇寫入時機(jī),這樣有更好的性能表現(xiàn),又或者使用always,可以會讓響應(yīng)變慢一些但是數(shù)據(jù)的安全性會更高,如果不確定選哪種的話,那就用everysec吧
no-appendfsync-on-rewrite
默認(rèn)配置:no-appendfsync-on-rewrite no
,當(dāng)AOF fsync策略是always或者everysec,會啟動一個后臺進(jìn)程(后臺進(jìn)行保存或者AOF文件的后臺重寫),該進(jìn)程會在磁盤上頻繁的I/O,在一些Linux配置下Redis的fsync() 調(diào)用可能會阻塞太久,需要注意的是目前還沒有相應(yīng)的優(yōu)化策略,極端情況下在不同線程進(jìn)行的fsync可能阻塞同步的write(2)調(diào)用,為了減緩上面提到的問題,可以在主線程調(diào)用BGSAVE或者BGREWRITEAOF命名避免fsync()在主線程上調(diào)用,這意味著當(dāng)其他的子節(jié)點(diǎn)在保存的時候,Redis的持久化就和appendfsync no
策略一樣,這意味著在實(shí)際中的最糟糕的場景下(在默認(rèn)的Linux配置下)有可能丟失超過30s時間粒度的log,如果應(yīng)用不能忍受延遲問題,將選項(xiàng)配置為yes,否則保持為no,這樣在持久化的角度上是最安全的選擇。
auto-aof-rewtire-percentage、auto-aof-rewrite-min-size
默認(rèn)配置:auto-aof-rewtire-percentage 100 、 auto-aof-rewrite-min-size 64mb
自動重寫aof文件,Redis支持調(diào)用BGREWRITEAOF命名,并在AOF文件達(dá)到特定的百分比的時候自動重寫AOF文件,一般是這么工作的:Redis會記錄最近一次重寫后的AOF文件大?。ㄈ绻麊雍鬀]有重寫過,則記錄啟動時的AOF文件大?。?,基礎(chǔ)的文件大小和當(dāng)前的文件大小進(jìn)行比較,如果當(dāng)前的大小比配置的百分比大,則觸發(fā)重寫操作。同時也應(yīng)該配置一個觸發(fā)重寫的最小文件大小,這么做可以避免當(dāng)AOF文件達(dá)到了配置的百分比,但是AOF文件還是很小的情況觸發(fā)重寫操作,配置百分比為0意味著關(guān)閉自動重寫AOF的特性。
aof-load-truncated
默認(rèn)值:aof-load-truncated yes
,當(dāng)AOF文件的數(shù)據(jù)加載到內(nèi)存的時候,AOF文件可能在Redis啟動的時候在末尾被截斷,這可能在跑Redis進(jìn)程的系統(tǒng)崩潰的情況下出現(xiàn),特別是當(dāng)一個ext4文件系統(tǒng)掛載的時候沒有使用data=ordered
選項(xiàng)(但是在Redis進(jìn)程自己崩潰或者中止,但是操作系統(tǒng)還正常運(yùn)行時,這種情況就不會發(fā)生),當(dāng)Redis發(fā)現(xiàn)AOF在末尾被截斷的時候,Redis可以主動退出進(jìn)程或者盡可能的加載更多的數(shù)據(jù)(目前的默認(rèn)行為)并正常啟動,如果aof-load-truncated設(shè)置成yes,Redis加載被截斷的AOF文件,redis啟動并將相關(guān)的信息寫到log中通知用戶有這一現(xiàn)象發(fā)生。如果設(shè)置成no,Redis錯誤充電并拒絕啟動,當(dāng)該配置設(shè)置為no的時候,就要求用戶在重啟服務(wù)前使用redis-check-aof
來修復(fù)AOF文件。
注意:如果AOF文件的中間位置出現(xiàn)了問題,Redis仍會錯誤退出。這個配置選項(xiàng)只在Redis想從AOF文件中讀取更多數(shù)據(jù)但是實(shí)在沒有新的可以讀取的情況下才有作用。
aof-use-rdb-preamble
默認(rèn)配置:aof-use-rdb-preamble yes
,當(dāng)重寫AOF文件的時候,Redis也可以在AOF文件在開頭應(yīng)用RDB文件來更快的重寫和恢復(fù)。當(dāng)該配置選項(xiàng)開啟,AOF文件的重寫組成由這兩部分組成:[RDB file][AOF tail]
,Redis加載AOF文件的時候發(fā)現(xiàn)AOF文件里由"REDIS"字符串打頭,Redis就會加載預(yù)先的RDB文件,接著在尾部加載AOF文件。
生產(chǎn)常見配置
安全配置
requirepass
配置格式:requirepass password
,要求客戶端先使用命令A(yù)UTH進(jìn)行認(rèn)證,才能處理其他命令
rename-command
配置格式:rename-command CONFIG abcdef
,命令重命名,可以在環(huán)境中重命名那些比較危險的命令,比如把CONFIG命令重命名成一個不好猜的名字,這樣內(nèi)部的功能還可以使用,且可以避免大部分的客戶端使用
客戶端配置
maxclients
默認(rèn)配置:maxclients 10000
,設(shè)置可以同時連接客戶端的最大數(shù)量,一旦達(dá)到該限制數(shù)Redis會拒絕所有的新連接并返回錯誤信息max number of clients reached
內(nèi)存管理
maxmemory
配置格式:maxmemory
,設(shè)置限定的最大內(nèi)存使用,當(dāng)內(nèi)存使用達(dá)到限制Redis會根據(jù)配置的淘汰策略(見maxmemory-policy)移除鍵值對,如果根據(jù)淘汰策略,Redis不能移除鍵值對,Redis會拒絕那些申請更大內(nèi)存的命令,比如SET,LPUSH等等,但是仍可以處理讀請求,比如GET等,該選項(xiàng)對那些使用Redis進(jìn)行LRU,LFU緩存系統(tǒng)或者硬性限制內(nèi)存很友好(使用noeviction策略),如果為實(shí)例配置了maxmemory,且該實(shí)例配置了子節(jié)點(diǎn),那么已使用內(nèi)存的大小就需要加上為副本配置的輸出緩沖區(qū)的大小。這樣因?yàn)榫W(wǎng)絡(luò)問題/重新同步不會一直觸發(fā)鍵的淘汰行為。相反的,副本緩沖區(qū)中充滿了對鍵的刪除或淘汰的情況可能觸發(fā)更多key被淘汰,以此類推直到庫完全被清空。簡單說就是,如果為實(shí)例配置了副本,那么建議設(shè)置一個較低的maxmemory值,這樣系統(tǒng)中就有更多的內(nèi)存空間留給副本緩沖區(qū)(如果淘汰策略是‘noeviction’那上面說的就沒有必要)
maxmemory-policy
默認(rèn)配置:maxmemory-policy noeviction
,在內(nèi)存使用達(dá)到maxmemory后,Redis如何選擇鍵值對進(jìn)行淘汰。有以下幾種:
- volatile-lru:使用LRU算法,在設(shè)置了過期時間的key中選擇
- allkeys-lru:使用LRU算法,在所有的key中選擇
- volatile-lfu:使用LFU算法,在設(shè)置了過期時間key中選擇
- allkeys-lfu:使用LFU算法,在所有的key中選擇
- volatile-random:在設(shè)置了過期時間的key中隨機(jī)選擇
- allkeys-random:在所有key中隨機(jī)選擇
- volatile-ttl:在設(shè)置了過期時間的key中,選擇過期時間最近的key
- noeviction:不淘汰key,對任何寫操作(使用額外內(nèi)存)返回錯誤
LRU 代表最近最少使用
LFU 代碼最近最不常使用
LRU,LFU和volatile-ttl均由近似的隨機(jī)算法實(shí)現(xiàn)
不管采用了以上的哪種策略,對于新的寫請求,如果沒有合適的key可以淘汰,Redis均會響應(yīng)一個error
[post cid=“625” cover=“https://resource.if010.com/redis_maxmemory_policy_banner.jpg” size=“”/]
maxmemory-samples
默認(rèn)配置:maxmemory-samples 5
,LRU、LFU 以及最小TTL的實(shí)現(xiàn)都不是精確的而是比較粗略的近似算法(為了節(jié)省內(nèi)存),為了速度或者精確度,可以進(jìn)行相應(yīng)的配置。默認(rèn)Redis會檢查5個key,在其中選擇最近最少使用的,也可以直接在下面的配置項(xiàng)中配置 Redis 選擇的樣本數(shù)量,默認(rèn)配置的值5,已經(jīng)可以有一個很完美的結(jié)果,10的話可能會讓選擇策略更像真正意義上的LRU算法,但是需要更多CPU資源,3的話會更快,但是不夠精確
replica-ignore-maxmemory
默認(rèn)配置:replica-ignore-maxmemory yes
,從Redis 5.0之后,副本默認(rèn)會忽略為其配置的maxmemory選項(xiàng)(除非因?yàn)楣收限D(zhuǎn)移(failover)或者選擇將其晉升為主節(jié)點(diǎn)),也就是說key的淘汰只會由主節(jié)點(diǎn)執(zhí)行,副本對應(yīng)的是主節(jié)點(diǎn)發(fā)送對應(yīng)的刪除命令給副本作為key的淘汰方式,這個行為模式保證了主副節(jié)點(diǎn)的一致性,但是如果副本是可寫的或者你想要你的副本有不同的內(nèi)存配置,而且你也很確認(rèn)到達(dá)副本的寫操作能保證冪等性(idempotenet),那你可以修改這個默認(rèn)值(但是最好保證你理解了這么做的原因)
提示:因?yàn)楦北灸J(rèn)沒有maxmemory和淘汰策略,副本實(shí)際的內(nèi)存占用可能比maxmemeory配置的值大(可能因?yàn)楦北揪彌_區(qū),或者某些數(shù)據(jù)結(jié)構(gòu)占用了額外的內(nèi)存等等原因)。所以確保對副本有合適的監(jiān)控手段,保證在主節(jié)點(diǎn)達(dá)到配置的maxmemory設(shè)置之前,副本有足夠的內(nèi)存保證不會出現(xiàn)真正的out-of-memory條件
主從配置
replicaof
配置格式:replicaof masterip masterport
,主從復(fù)制,使用replicaof來讓一個Redis實(shí)例復(fù)制另一個Redis實(shí)例,Redis復(fù)制是異步進(jìn)行的,但是可以通過配置讓Redis主節(jié)點(diǎn)拒絕寫請求:配置會給定一個值,主節(jié)點(diǎn)至少需要和大于該值的從節(jié)點(diǎn)個數(shù)成功連接,如果 Redis 從節(jié)點(diǎn)和主節(jié)點(diǎn)意外斷連了很少的一段時間,從節(jié)點(diǎn)可以向主節(jié)點(diǎn)進(jìn)行增量復(fù)制,復(fù)制會自動進(jìn)行且不需要人為介入
masterauth
配置格式:masterauth master-password
,如果主節(jié)點(diǎn)配置了密碼(使用了"requirepass"配置項(xiàng)),從節(jié)點(diǎn)需要進(jìn)行密碼認(rèn)證才能進(jìn)行復(fù)制同步的過程,否則主節(jié)點(diǎn)會直接拒絕從節(jié)點(diǎn)的復(fù)制請求
replica-serve-stale-data
默認(rèn)配置:replica-serve-stale-data yes
,當(dāng)復(fù)制過程與主節(jié)點(diǎn)失去連接,或者當(dāng)復(fù)制正在進(jìn)行時,復(fù)制可以有兩種行為模式:
- 如果replica-serve-stale-data設(shè)置為’yes’(默認(rèn)設(shè)置),從節(jié)點(diǎn)仍可以處理客戶端請求,但該從節(jié)點(diǎn)的數(shù)據(jù)很可能和主節(jié)點(diǎn)不同步,如果這是與主節(jié)點(diǎn)進(jìn)行的第一次同步,從節(jié)點(diǎn)的數(shù)據(jù)也可能是空數(shù)據(jù)集
- 如果replica-serve-stale-data設(shè)置成’no’,從節(jié)點(diǎn)會對除了INFO、replicaOF、AUTH、PING、SHUTDOWN、REPLCONF、ROLE、CONFIG、SUBSCRIBE、UNSUBSCRIBE、PSUBSCRIBE、PUNSUBSCRIBE、PUBLISH、PUBSUB、COMMAND、POST、HOST:and LATENCY這些命令之外的請求均返回"SYNC with master in process"
replica-read-only
默認(rèn)配置:replica-read-only yes
,可以配置從節(jié)點(diǎn)是否可以處理寫請求。針對從節(jié)點(diǎn)開啟寫權(quán)限來存儲時效低的(ephemeral)數(shù)據(jù)可能是一種有效的方式(因?yàn)閷懭氲綇墓?jié)點(diǎn)的數(shù)據(jù)很可能隨著重新同步而被刪除),但是開啟該配置也會導(dǎo)致一些問題。從Redis 2.6開始從節(jié)點(diǎn)默認(rèn)是僅可讀的
repl-diskless-sync
默認(rèn)配置:repl-diskless-sync no
,同步復(fù)制策略:硬盤或者套接字(不使用硬盤的復(fù)制策略目前還在實(shí)驗(yàn)階段)新建立連接和重連的副本不會根據(jù)數(shù)據(jù)情況進(jìn)行恢復(fù)傳輸,只會進(jìn)行全量復(fù)制,主節(jié)點(diǎn)會傳輸在從節(jié)點(diǎn)之間傳輸RDB文件
傳輸行為有兩種方式:
硬盤備份:Redis主節(jié)點(diǎn)創(chuàng)建一個子進(jìn)程來向硬盤寫RDB文件,之后由父進(jìn)程持續(xù)的文件傳給副本
不使用硬盤:Redis主節(jié)點(diǎn)建立一個進(jìn)程直接向副本的網(wǎng)絡(luò)套接字寫RDB文件,不涉及到硬盤
對于方式1,在生成RDB文件時,多個副本會進(jìn)行入隊(duì)并在當(dāng)前子進(jìn)程完成RDB文件時立即為副本進(jìn)行RDB傳輸,而對于方式2,一旦傳輸開始,新來的副本傳輸請求會入隊(duì)且只在當(dāng)前的傳輸斷開后才建立新的傳輸連接,如果使用方式2,主節(jié)點(diǎn)會等待一段時間,根據(jù)具體的配置,等待是為了可以在開始傳輸前可以有期望的副本同步請求到達(dá),這樣可以使用并行傳輸提高效率,對于配置是比較慢的硬盤,而網(wǎng)絡(luò)很快(帶寬大)的情況下,使用方式2進(jìn)行副本同步會更適合
repl-diskless-sync-delay
默認(rèn)配置:repl-diskless-sync-delay 5
,如果diskless sync是開啟的話,就需要配置一個延遲的秒數(shù),這樣可以服務(wù)更多通過socket傳輸RDB文件的副本,這個配置很重要,因?yàn)橐坏﹤鬏旈_始,就不能為新來的副本傳輸服務(wù),只能入隊(duì)等待下一次RDB傳輸,所以該配置一個延遲的值就是為了讓更多的副本請求到達(dá),延遲配置的單位是秒,默認(rèn)是 5 秒,不想要該延遲的話可以配置為 0 秒,傳輸就會立即開始
repl-ping-replica-period
默認(rèn)配置:repl-ping-replica-period 10
,副本會根據(jù)配置好的時間間隔(interval)向主節(jié)點(diǎn)發(fā)送PING命令,可以通過repl_ping_replica_period配置修改時間間隔,默認(rèn)為10秒
repl-timeout
默認(rèn)配置:repl-timeout 60
,配置副本進(jìn)行超時處理,在副本的角度,在同步過程中批量進(jìn)行I/O傳輸,從副本s的角度,主節(jié)點(diǎn)超時了,從主節(jié)點(diǎn)的角度,副本超時了,需要重視的一點(diǎn)是確保該選項(xiàng)的配置比repl-ping-replica-period配置的值更高,否則每次主從之間的網(wǎng)絡(luò)比較擁擠時就容易被判定為超時
repl-disable-tcp-nodelay
默認(rèn)配置:repl-disable-tcp-nodelay no
,同步過后在副本套接字上關(guān)閉TCP_NODELAY,如果選擇了’yes’,Redis會使用很小的TCP包,占用很低的帶寬來想副本發(fā)送數(shù)據(jù),但是這么做到達(dá)副本的數(shù)據(jù)會有一些延遲,使用默認(rèn)的配置值且是Linux內(nèi)核該延遲最多可能40毫秒,如果選擇’no’,副本的數(shù)據(jù)延遲會更低但是占用的帶寬會更多一些,默認(rèn)會為了低延遲進(jìn)行優(yōu)化,但是在比較擁擠網(wǎng)絡(luò)情況下或者是主節(jié)點(diǎn)和副本之間的網(wǎng)絡(luò)情況比較復(fù)雜,比如中間有很多路由跳轉(zhuǎn)的情況下,把選項(xiàng)設(shè)置為’yes’應(yīng)該會比較適合
repl-backlog-size
默認(rèn)配置:repl-backlog-size 1mb
,配置副本的緩沖區(qū)(backlog)大小,該緩沖區(qū)用來在副本斷開連接后暫存副本數(shù)據(jù),這樣做是因?yàn)楦北局匦逻B接后,不一定要重新進(jìn)行全量復(fù)制,很多時候增量復(fù)制同步(僅同步斷連期間副本可能丟失的數(shù)據(jù))完全足夠了,配置的緩沖區(qū)越大,副本可以承受的斷連時間可以更長,至少有一個副本連接時緩沖區(qū)才會進(jìn)行分配
repl-backlog-ttl
默認(rèn)配置:repl-backlog-ttl 3600
,主節(jié)點(diǎn)如果一段時間沒有副本連接,上面提到的緩沖區(qū)會被釋放,可以通過配置一個指定的時間來釋放緩沖區(qū),如果主節(jié)點(diǎn)在這個時間內(nèi)還沒有與新的副本建立連接,需要注意的是副本不會因?yàn)槌瑫r釋放緩沖區(qū),因?yàn)楦北究赡軙粫x升(promot)為主節(jié)點(diǎn),需要保持對其他副本進(jìn)行增量復(fù)制的能力:因此他們總是積累緩沖區(qū),配置為’0’意味著不釋放緩沖區(qū)
replica-priority
默認(rèn)配置:replica-priority 100
,副本的優(yōu)先級是一個整型數(shù)字,可以由Redis的INFO命令顯示,優(yōu)先級的作用在于當(dāng)主節(jié)點(diǎn)無法提供服務(wù)后,Redis哨兵會使用到優(yōu)先級進(jìn)行選舉副本,晉升為主節(jié)點(diǎn),值越低,代表該副本晉升成為主節(jié)點(diǎn)的優(yōu)先級越高,比如說有三個副本,優(yōu)先級的值分別為10、100、25,Redis哨兵會選擇最低的那個,即優(yōu)先級配置為10的那個,但是,一個特殊的配置值’0’,意味著該副本不可能充當(dāng)主節(jié)點(diǎn)的角色,故優(yōu)先級配置為0的副本永遠(yuǎn)不會被Redis哨兵選擇晉升。默認(rèn)的優(yōu)先級配置是100
min-replicas-to-write 、 min-replicas-max-lag
主節(jié)點(diǎn)可以根據(jù)目前連接的延遲慢于M秒的副本數(shù)量,選擇是否拒絕寫請求,數(shù)量N的副本需要是"online"的狀態(tài),延遲的秒數(shù)(The lag(落后) in seconds)M,計算方式是根據(jù)上一次副本發(fā)送ping命令到主節(jié)點(diǎn)的時間計算,通常每秒都會發(fā)送ping命令,這個選項(xiàng)不保證N個副本會接受寫請求,但是如果沒有足夠的副本可用,則會限制那些丟失寫請求的暴露窗口至特定的秒數(shù),比如要求至少有三個延遲小等于10秒的副本,可以這么配置:
# 配置設(shè)置為 0 會關(guān)閉該功能。 # 默認(rèn)的 min-replicas-to-write 被設(shè)置為 0(功能關(guān)閉) # min-replicas-max-lag 設(shè)置為 10. min-replicas-to-write 3 min-replicas-max-lag 10
replica-announce-ip 、 replica-announce-port
主節(jié)點(diǎn)應(yīng)該有多種方式來列舉出依附與它的副本的信息(ip和port),比如"INFO replication"就可以提供這些信息,它也會被其他的功能使用,比如Redis哨兵就會使用該命令列舉副本實(shí)例,還有一種方式是在主節(jié)點(diǎn)運(yùn)行"ROLE"命令來獲取這些信息
副本獲取監(jiān)聽的IP和地址分別通過以下的方式:
- IP:IP地址在副本和主節(jié)點(diǎn)建立的socket連接中自動被檢測到
- Port:端口信息會在副本進(jìn)行復(fù)制的TCP握手中交流傳遞,端口也是副本用來監(jiān)聽連接的一部分
如果使用了端口轉(zhuǎn)發(fā)或者NAT(Network Address Translation),實(shí)際連接到副本很可能通過的是不同的IP和端口對。下面的兩個配置選項(xiàng)用來讓副本上報特定的IP和端口集合給它連接的主節(jié)點(diǎn),之后主節(jié)點(diǎn)使用"INFO"或者"ROLE"命令都可以輸出這些上報的值
# 如果只想上報ip或端口其中一個,就沒有必要兩個都使用 replica-announce-ip 1.1.1.1 replica-announce-port 6379
集群配置
cluster-enabled
默認(rèn)配置:cluster-enabled yes
,是否打開集群模式
cluster-config-file
默認(rèn)配置:cluster-config-file nodes-6379.conf
,設(shè)定節(jié)點(diǎn)配置文件名
cluster-node-timeout
默認(rèn)配置:cluster-node-timeout 15000
,設(shè)定節(jié)點(diǎn)失聯(lián)時間,超過該時間(毫秒),集群自動進(jìn)行主從切換
cluster-require-full-coverage
默認(rèn)配置:cluster-require-full-coverage yes
,如果某一段插槽的主從都掛掉,而cluster-require-full-coverage為yes,那么 ,整個集群都掛掉,反之,cluster-require-full-coverage配置為no,那么,該插槽數(shù)據(jù)全都不能使用,也無法存儲
其他配置
CLUSTER DOCKER/NAT support
在某些部署情況中,Redis集群節(jié)點(diǎn)可能會出現(xiàn)地址發(fā)現(xiàn)失敗,原因是地址是NAT-ted或者端口轉(zhuǎn)發(fā)(一個典型的場景就是 Docker 或者其他容器),為了讓 Redis 集群在這種環(huán)境下正常工作,就需要個靜態(tài)的配置文件來讓集群節(jié)點(diǎn)知曉他們的公共地址,下面選項(xiàng)就有這個作用:
# 如果只想上報ip或端口其中一個,就沒有必要兩個都使用 replica-announce-ip 1.1.1.1 replica-announce-port 6379
SLOW LOG(慢日志)
默認(rèn)配置:slowlog-log-slower-than 10000 、slowlog-max-len 128
,Redis的慢日志用來記錄那些執(zhí)行了超過特定時間的查詢行為。這里的執(zhí)行時間不包括I/O操作,比如和客戶端的通信,發(fā)送回復(fù)的時間等等,而應(yīng)該只是執(zhí)行了這個命令本身需要的時間(就是說執(zhí)行這個命令期間,線程會阻塞且不會同時響應(yīng)其他的請求),慢日志有兩個屬性可以配置:一個用來告訴Redis執(zhí)行時間的定義,什么樣的執(zhí)行時間才要被記錄,另一個用來配置慢日志的長度,記錄一個新的命令,隊(duì)列中的最舊的命令會被移除,要注意的是配置的時間單位為微秒,所以1000000相當(dāng)于1秒,如果配置的是負(fù)值,慢日志則不起作用,如果是0的話,慢日志則會記錄每個命令,長度的配置沒有任何限制,但是主要內(nèi)存的消耗,可以使用慢日志的SLOWLOG RESET來回收內(nèi)存
LATENCY MONITOR(延遲監(jiān)控)
默認(rèn)配置:latency-monitor-threshold 0
,Redis的延遲監(jiān)控系統(tǒng)會在Redis運(yùn)行期間以不同的操作對象為樣本,收集和Redis實(shí)例相關(guān)的延遲行為,用戶可以通過LETENCY命令,打印相關(guān)的圖形信息和獲取相關(guān)的報告,延遲監(jiān)控系統(tǒng)只會收集那些執(zhí)行時間超過了我們通過latency-monitor-threshold配置的值的操作,當(dāng)latency-monitor-threshold的值設(shè)置為0的時候,延遲監(jiān)控系統(tǒng)就會關(guān)閉,默認(rèn)情況下延遲監(jiān)控是關(guān)閉的,因?yàn)榇蠖鄶?shù)情況下可能沒有延遲相關(guān)的問題,而且收集數(shù)據(jù)對性能表現(xiàn)是有影響的,雖然影響很小,但是在系統(tǒng)高負(fù)載運(yùn)行情況下還是不能忽視的,延遲監(jiān)控系統(tǒng)可以在運(yùn)行期間使用CONFIG SET latency-monitor-threshold milliseconds
開啟
LAZY FREEING(懶釋放)
Redis有兩個可以刪除key的原語(primitive),其中一種是調(diào)用DEL,阻塞地刪除對象。也就是說Redis Server需要通過同步的方式確認(rèn)回收了所有和剛才刪除的key相關(guān)的內(nèi)存后,才能處理接下來的命令。如果要刪除的key很小,執(zhí)行DEL命令的時間也很短,和其他時間復(fù)雜度為O(1)或O(log_N)的命令差不多。但是,如果要刪除的key涉及到一個存儲著百萬級別元素的集合,Redis Server就可能因此阻塞一段時間(甚至到秒的級別)
由于同步的處理方式可能帶來的問題,Redis提供了非阻塞的刪除原語比如UNLINK以及異步的選項(xiàng)比如FLUSHALL和FLUSHDB命名,為的就是在后臺回收內(nèi)存,這些命名會在固定時間執(zhí)行(in constant time),另外的線程會在后臺以盡可能快的速度釋放這些對象
DEL、UNLINK和帶有ASYNC選項(xiàng)的FLUSHALL和FLUSHDB命名都可以由用戶控制,這取決于應(yīng)用層面是否理解且合適的使用相應(yīng)的命令來達(dá)到目的,但是還是有一些情況要注意,Redis有時會因?yàn)槠渌僮鞯母弊饔脤?dǎo)致觸發(fā)key 的刪除或者刷新整個數(shù)據(jù)庫,特別是在用戶調(diào)用了對象刪除的以下場景:
- 在淘汰策略下,因?yàn)榕渲昧薽axmemory和maxmemory policy,為了在不超過配置的內(nèi)存限制下騰出空間給新來的數(shù)據(jù)
- 因?yàn)檫^期時間的配置,當(dāng)一個key配置了expire時間且時間到了,那它必須從內(nèi)存中移除。命名在已經(jīng)存在的key上進(jìn)行數(shù)據(jù)的存儲操作的副作用。比如RENAME命名在替換的時候需要刪除原本的key的內(nèi)容。類似的帶有STORE選項(xiàng)的SUNIONSTORE或者SORT命名可能會刪除已存在的key。SET命令本身為了用新的值替換,會將要操作的key的舊值先刪除掉。在REPLICATION期間,當(dāng)副本執(zhí)行了全量同步復(fù)制,副本的整個數(shù)據(jù)庫會被清空,然后加載傳輸來的RDB文件。
上面的場景在默認(rèn)情況下都是以阻塞的方式刪除對象,比如調(diào)用DEL的時候。你在本配置項(xiàng)中為每個場景進(jìn)行配置,這樣就可以像 UNLINK 被調(diào)用時以非阻塞的方式釋放內(nèi)存
lazyfree-lazy-eviction no lazyfree-lazy-expire no lazyfree-lazy-server-del no lazyfree-lazy-flush no
附錄:關(guān)于哨兵的常規(guī)命令
常用命令
PING
返回 PONG。
SENTINEL masters
列出所有被監(jiān)視的主服務(wù)器,以及這些主服務(wù)器的當(dāng)前狀態(tài)。
SENTINEL slaves
列出給定主服務(wù)器的所有從服務(wù)器,以及這些從服務(wù)器的當(dāng)前狀態(tài)。
SENTINEL get-master-addr-by-name
返回給定名字的主服務(wù)器的 IP 地址和端口號。 如果這個主服務(wù)器正在執(zhí)行故障轉(zhuǎn)移操作, 或者針對這個主服務(wù)器的故障轉(zhuǎn)移操作已經(jīng)完成, 那么這個命令返回新的主服務(wù)器的 IP 地址和端口號。
SENTINEL reset
重置所有名字和給定模式 pattern 相匹配的主服務(wù)器。 pattern 參數(shù)是一個 Glob 風(fēng)格的模式。 重置操作清除主服務(wù)器目前的所有狀態(tài), 包括正在執(zhí)行中的故障轉(zhuǎn)移, 并移除目前已經(jīng)發(fā)現(xiàn)和關(guān)聯(lián)的, 主服務(wù)器的所有從服務(wù)器和 Sentinel 。
SENTINEL failover
當(dāng)主服務(wù)器失效時, 在不詢問其他 Sentinel 意見的情況下, 強(qiáng)制開始一次自動故障遷移 (不過發(fā)起故障轉(zhuǎn)移的 Sentinel 會向其他 Sentinel 發(fā)送一個新的配置,其他 Sentinel 會根據(jù)這個配置進(jìn)行相應(yīng)的更新)。
ACL(>=6.2)
此命令管理Sentinel訪問控制列表。有關(guān)更多信息,請參閱ACL文檔頁面和Sentinel訪問控制列表驗(yàn)證。
AUTH(>=5.0.1)
對客戶端連接進(jìn)行身份驗(yàn)證。有關(guān)更多信息,請參閱AUTH命令和配置帶有身份驗(yàn)證的Sentinel實(shí)例部分。
CLIENT
此命令管理客戶端連接。有關(guān)詳細(xì)信息,請參閱其子命令頁面。
COMMAND(>=6.2)
此命令返回有關(guān)命令的信息。有關(guān)詳細(xì)信息,請參閱COMMAND命令及其各種子命令。
HELLO(>=6)
切換連接的協(xié)議。有關(guān)詳細(xì)信息,請參閱HELLO命令。
INFO
返回有關(guān)Sentinel服務(wù)器的信息和統(tǒng)計信息。有關(guān)更多信息,請參閱INFO命令。
ROLE
此命令返回字符串“sentinel”和受監(jiān)控主機(jī)的列表。
SHUTDOWN
關(guān)閉Sentinel實(shí)例。
其他命令
SENTINEL CONFIG GET<name>(>=6.2)
獲取全局SENTINEL配置參數(shù)的當(dāng)前值。指定的名稱可以是通配符,類似于Redis CONFIG GET命令。
SENTINEL CONFIG SET<name><value>(>=6.2)
設(shè)置全局SENTINEL配置參數(shù)的值。
SENTINEL CKQUORUM<master name>
檢查當(dāng)前SENTINEL配置是否能夠達(dá)到故障轉(zhuǎn)移主機(jī)所需的仲裁,以及授權(quán)故障轉(zhuǎn)移所需的多數(shù)仲裁。該命令應(yīng)在監(jiān)控系統(tǒng)中使用,以檢查Sentinel部署是否正常。
SENTINEL FLUSHCONFIG
強(qiáng)制SENTINEL在磁盤上重寫其配置,包括當(dāng)前的SENTINEL狀態(tài)。通常情況下,每當(dāng)狀態(tài)發(fā)生變化時,Sentinel都會重寫配置(在重新啟動時保留在磁盤上的狀態(tài)子集的上下文中)。但是,有時配置文件可能會因?yàn)椴僮麇e誤、磁盤故障、包升級腳本或配置管理器而丟失。在這些情況下,強(qiáng)制Sentinel重寫配置文件的方法很方便。即使以前的配置文件完全丟失,此命令也能工作。
SENTINEL FAILOVER<master name>
強(qiáng)制進(jìn)行故障切換,就好像無法訪問主機(jī)一樣,并且不要求與其他SENTINEL達(dá)成一致(但是,將發(fā)布新版本的配置,以便其他Sentinels更新其配置)。
1.不會與其他Sentinel進(jìn)行協(xié)商;
2.轉(zhuǎn)移完成后會通知其他Sentinel節(jié)點(diǎn)(根據(jù)轉(zhuǎn)移結(jié)果進(jìn)行更新);
SENTINEL GET-MASTER-ADDR-BY-NAME<MASTER NAME>
返回具有該名稱的主機(jī)的ip和端口號。如果此主機(jī)的故障轉(zhuǎn)移正在進(jìn)行或已成功終止,它將返回升級的復(fù)制副本的地址和端口。
SENTINEL INFO-CACHE(>=3.2)
從主控和副本返回緩存的INFO輸出。
SENTINEL IS-MASTER-DOWN-BY-ADDR
檢查ip:port指定的主機(jī)是否從當(dāng)前SENTINEL的角度關(guān)閉。此命令主要用于內(nèi)部使用。
為*時,Sentinel節(jié)點(diǎn)直接交換對主節(jié)點(diǎn)下線的判斷;為運(yùn)行ID時,Sentinel節(jié)點(diǎn)希望其他Sentinel節(jié)點(diǎn)投票自己成為領(lǐng)導(dǎo)者Sentinel(運(yùn)行ID為Sentinel的運(yùn)行ID)返回值由以下3個參數(shù)構(gòu)成:
返回參數(shù)說明
down_state 0:代表Redis主節(jié)點(diǎn)仍在線 ;1:代表Redis主節(jié)點(diǎn)已下線
leader_runid *:不同意做為領(lǐng)導(dǎo)者運(yùn)行;Sentinel ID:該運(yùn)行ID代表的Sentinel同意
leader_epoch 領(lǐng)導(dǎo)者
SENTINEL MASTER<MASTER name>
顯示指定主機(jī)的狀態(tài)和信息。
SENTINEL MASTERS
顯示受監(jiān)控主機(jī)及其狀態(tài)的列表。
SENTINEL MONITOR
啟動SENTINEL的監(jiān)控。
SENTINEL MYID(>=6.2)
返回SENTINEL實(shí)例的ID。
SENTINEL PENDING-SCRIPTS
此命令返回有關(guān)掛起腳本的信息。
SENTINEL REMOVE
停止哨兵的監(jiān)控。
SENTINEL REPLICAS<master name>(>=5.0)
顯示此master的副本列表及其狀態(tài)。老版本可以用SENTINEL SENTINELS <master name>
SENTINEL SENTINELS<master name>
顯示此master的SENTINEL實(shí)例及其狀態(tài)的列表。
SENTINEL SET
設(shè)置SENTINEL的監(jiān)控配置。
SENTINEL SIMULATE-FAILURE(選舉后崩潰|晉升后崩潰|幫助)(>=3.2)
此命令模擬不同的SENTINEL崩潰場景。
SENTINEL RESET<pattern>
此命令將重置具有匹配名稱的所有主機(jī)。模式參數(shù)是glob樣式的模式。重置過程會清除主機(jī)中以前的任何狀態(tài)(包括正在進(jìn)行的故障轉(zhuǎn)移),并刪除已發(fā)現(xiàn)并與主機(jī)關(guān)聯(lián)的每個復(fù)制副本和哨兵。
到此這篇關(guān)于Redis的四種部署方案的文章就介紹到這了,更多相關(guān)Redis部署內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
使用Redis實(shí)現(xiàn)記錄訪問次數(shù)的三種方案
這篇文章主要介紹了使用Redis實(shí)現(xiàn)記錄訪問次數(shù)的三種方案,文中通過代碼示例和圖文講解的非常詳細(xì),對大家的學(xué)習(xí)或工作有一定的幫助,需要的朋友可以參考下2024-09-09Redis數(shù)據(jù)備份與恢復(fù)方式的五種方式
本文主要介紹了Redis數(shù)據(jù)備份與恢復(fù)方式,包含了五種方式,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2024-07-07

Redission實(shí)現(xiàn)分布式鎖lock()和tryLock()方法的區(qū)別小結(jié)

Redis序列化設(shè)置以及jetcache連接Redis序列化的設(shè)置過程

redis延時隊(duì)列的項(xiàng)目實(shí)踐