Redis是咱們當下比較流行使用的非關係數據庫,可支持多樣化的數據類型,多線程高併發支持,redis運行在內存擁有更快的讀寫。由於redis的表現如此出色,如何能保障redis在運行中可以應對宕機故障,linux
因此今天總結了下redis主從高可用的搭建,參考了網上一些大神的博客文章,發現不少都是有坑的,因此本人在此分享一次,但願能幫助到你們。redis
Redis 是徹底開源免費的,遵照BSD協議,是一個高性能的key-value數據庫。數據庫
Redis 與其餘 key - value 緩存產品有如下三個特色:vim
Redis支持數據的持久化,能夠將內存中的數據保持在磁盤中,重啓的時候能夠再次加載進行使用。設計模式
Redis不只僅支持簡單的key-value類型的數據,同時還提供如:字符串(String), 哈希(Map), 列表(list), 集合(sets) 和有序集合(sorted sets)等數據結構的存儲。緩存
Redis支持數據的備份,即master-slave模式的數據備份。bash
性能極高 – Redis能讀的速度是100K+次/s,寫的速度是80K+次/s 。服務器
豐富的數據類型 – Redis支持二進制案例的 Strings, Lists, Hashes, Sets 及 Ordered Sets 數據類型操做。數據結構
原子 – Redis的全部操做都是原子性的,同時Redis還支持對幾個操做全並後的原子性執行。多線程
豐富的特性 – Redis還支持 publish/subscribe, 通知, key 過時等等特性。
Centos7 --> 172.16.81.140 -->主Redis -->主Keepalived
Centos7 --> 172.16.81.141 -->從Redis -->備Keepalived
VIP --> 172.16.81.139
redis(通常3.0版本以上都行)
KeepAlived(直接在線安裝的)
Redis編譯安裝
一、提早準備好的redis軟件放在/opt目錄下:redis-4.0.6.tar.gz
cd /opt
tar -zxvf redis-4.0.6.tar.gz
mv redis-4.0.6 redis
cd redis
makeMALLOC=libc
make PREFIX=/usr/local/redis install
二、配置redis啓動腳本
vim /etc/init.d/redis
#!/bin/sh
#chkconfig:2345 80 90
# Simple Redisinit.d script conceived to work on Linux systems
# as it doesuse of the /proc filesystem.
#配置redis端口號
REDISPORT=6379
#配置redis啓動命令路徑
EXE=/usr/local/redis/bin/redis-server
#配置redis鏈接命令路徑
CLIEXE=/usr/local/redis/bin/redis-cli
#配置redis運行PID路徑
PIDFILE=/var/run/redis_6379.pid
#配置redis的配置文件路徑
CONF="/etc/redis/redis.conf"
#配置redis的鏈接認證密碼
REDISPASSWORD=123456
function start () {
if [ -f $PIDFILE ]
then
echo "$PIDFILE exists,process is already running or crashed"
else
echo "Starting Redisserver..."
$EXE $CONF &
fi
}
function stop () {
if [ ! -f $PIDFILE ]
then
echo "$PIDFILE does not exist, process is not running"
else
PID=$(cat $PIDFILE)
echo "Stopping ..."
$CLIEXE -p $REDISPORT -a $REDISPASSWORD shutdown
while [ -x /proc/${PID} ]
do
echo "Waiting forRedis to shutdown ..."
sleep 1
done
echo "Redis stopped"
fi
}
function restart () {
stop
sleep 3
start
}
case "$1" in
start)
start
;;
stop)
stop
;;
restart)
restart
;;
*)
echo -e "\e[31m Please use $0 [start|stop|restart] asfirst argument \e[0m"
;;
esac
授予執行權限:chmod +x /etc/init.d/redis
添加開機啓動:
chkconfig --add redis
chkconfig redis on
查看:chkconfig --list | grep redis
這次試驗事先關閉了防火牆和selinux,生產環境建議開啓防火牆。
三、添加redis命令環境變量
#vi /etc/profile
#添加下一行參數
exportPATH="$PATH:/usr/local/redis/bin"
#環境變量生效
source /etc/profile
四、啓動redis服務
service redis start
#檢查啓動狀況
ps -ef | grep redis
注:在咱們兩臺服務器上先執行一樣的操做安裝完成redis,接下來安裝完成後,就直接進入配置主從環境。
引伸回到前面的設計模式,咱們的思路是以140做爲主,141做爲從,139做爲VIP飄逸地址,應用經過139的6379端口訪問redis數據庫。
正常運行下,當主節點140宕機後,VIP飄逸到141上,這時141就會接管140成爲主節點,140就會成爲從節點,繼續提供讀寫操做。
當140恢復正常後,這時140會與141進行一次數據同步,140原有的數據不會丟失,還會同步宕機之間已經寫入到141的數據,數據同步完成以後,
VIP會由於權重的緣由從新回到140節點上併成爲主節點,141會由於失去VIP會從新成爲從節點,恢復到初始狀態繼續提供不間斷的讀寫服務。
一、配置redis的配置文件
Master-140配置文件
vim /etc/redis/redis.conf
bind 0.0.0.0
port 6379
daemonize yes
requirepass 123456
slave-serve-stale-data yes
slave-read-only no
Slave-141配置文件
vim /etc/redis/redis.conf
bind 0.0.0.0
port 6379
daemonize yes
slaveof 172.16.81.140 6379
masterauth 123456
slave-serve-stale-data yes
slave-read-only no
二、配置完成後重啓redis服務!驗證主從是否正常。
主節點140終端登陸測試:
[root@localhost ~]# redis-cli -a 123456
127.0.0.1:6379> INFO
.
.
.
# Replication
role:master
connected_slaves:1
slave0:ip=172.16.81.141,port=6379,state=online,offset=105768,lag=1
master_replid:f83fcc3c98614d770f2205831fef1e877fa3f482
master_replid2:1f25604997a4ad3eb8344e8155990e78acd93312
master_repl_offset:105768
second_repl_offset:447
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:447
repl_backlog_histlen:105322
從節點141終端登陸測試:
[root@localhost ~]# redis-cli -a 123456
127.0.0.1:6379> info
.
.
.
# Replication
role:slave
master_host:172.16.81.140
master_port:6379
master_link_status:up
master_last_io_seconds_ago:5
master_sync_in_progress:0
slave_repl_offset:105992
slave_priority:100
slave_read_only:0
connected_slaves:0
master_replid:f83fcc3c98614d770f2205831fef1e877fa3f482
master_replid2:1f25604997a4ad3eb8344e8155990e78acd93312
master_repl_offset:105992
second_repl_offset:447
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:239
repl_backlog_histlen:105754
三、同步測試
主節點140
從節點141
到此redis的主從已經完成!
使用Keepalived實現VIP,而且經過notify_master、notify_backup、notify_fault、notify_stop來實現容災。
一、配置Keepalived配置文件
主Keepalived配置文件
vim /etc/keepalived/keepalived.conf
! Configuration File for keepalived
global_defs {
notification_email {
acassen@firewall.loc
failover@firewall.loc
sysadmin@firewall.loc
}
notification_email_from Alexandre.Cassen@firewall.loc
smtp_server 192.168.200.1
smtp_connect_timeout 30
router_id redis01
}
vrrp_script chk_redis {
script "/etc/keepalived/script/redis_check.sh"
interval 2
}
vrrp_instance VI_1 {
state MASTER
interface eno16777984
virtual_router_id 51
priority 100
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
track_script {
chk_redis
}
virtual_ipaddress {
172.16.81.139
}
notify_master /etc/keepalived/script/redis_master.sh
notify_backup /etc/keepalived/script/redis_backup.sh
notify_fault /etc/keepalived/script/redis_fault.sh
notify_stop /etc/keepalived/script/redis_stop.sh
}
備用Keepalived配置文件
vim /etc/keepalived/keepalived.conf
! Configuration File for keepalived
global_defs {
notification_email {
acassen@firewall.loc
failover@firewall.loc
sysadmin@firewall.loc
}
notification_email_from Alexandre.Cassen@firewall.loc
smtp_server 192.168.200.1
smtp_connect_timeout 30
router_id redis02
}
vrrp_script chk_redis {
script "/etc/keepalived/script/redis_check.sh"
interval 2
}
vrrp_instance VI_1 {
state BACKUP
interface eno16777984
virtual_router_id 51
priority 99
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
track_script {
chk_redis
}
virtual_ipaddress {
172.16.81.139
}
notify_master /etc/keepalived/script/redis_master.sh
notify_backup /etc/keepalived/script/redis_backup.sh
notify_fault /etc/keepalived/script/redis_fault.sh
notify_stop /etc/keepalived/script/redis_stop.sh
}
二、配置腳本
Master KeepAlived -- 140
建立存放腳本目錄:mkdir -p /etc/keepalived/script/
cd /etc/keepalived/script/
[root@localhost script]# cat redis_check.sh
#!/bin/bash
ALIVE=`/usr/local/redis/bin/redis-cli -a 123456 PING`
if [ "$ALIVE" == "PONG" ];then
echo $ALIVE
exit 0
else
echo $ALIVE
exit 1
fi
[root@localhost script]# cat redis_master.sh #!/bin/bash REDISCLI="/usr/local/redis/bin/redis-cli -a 123456" LOGFILE="/var/log/keepalived-redis-state.log" sleep 15 echo "[master]" >> $LOGFILE date >> $LOGFILE echo "Being master...." >>$LOGFILE 2>&1 echo "Run SLAVEOF cmd ...">> $LOGFILE $REDISCLI SLAVEOF 172.16.81.141 6379 >>$LOGFILE 2>&1 if [ $? -ne 0 ];then echo "data rsync fail." >>$LOGFILE 2>&1 else echo "data rsync OK." >> $LOGFILE 2>&1 fi sleep 10 #延遲10秒之後待數據同步完成後再取消同步狀態 echo "Run SLAVEOF NO ONE cmd ...">> $LOGFILE $REDISCLI SLAVEOF NO ONE >> $LOGFILE 2>&1 if [ $? -ne 0 ];then echo "Run SLAVEOF NO ONE cmd fail." >>$LOGFILE 2>&1 else echo "Run SLAVEOF NO ONE cmd OK." >> $LOGFILE 2>&1 fi
[root@localhost script]# cat redis_backup.sh #!/bin/bash REDISCLI="/usr/local/redis/bin/redis-cli -a 123456" LOGFILE="/var/log/keepalived-redis-state.log" echo "[backup]" >> $LOGFILE date >> $LOGFILE echo "Being slave...." >>$LOGFILE 2>&1 sleep 15 #延遲15秒待數據被對方同步完成以後再切換主從角色 echo "Run SLAVEOF cmd ...">> $LOGFILE $REDISCLI SLAVEOF 172.16.81.141 6379 >>$LOGFILE 2>&1
[root@localhost script]# cat redis_fault.sh
#!/bin/bash
LOGFILE=/var/log/keepalived-redis-state.log
echo "[fault]" >> $LOGFILE
date >> $LOGFILE
[root@localhost script]# cat redis_stop.sh
#!/bin/bash
LOGFILE=/var/log/keepalived-redis-state.log
echo "[stop]" >> $LOGFILE
date >> $LOGFILE
Slave KeepAlived -- 141
建立存放腳本目錄:mkdir -p /etc/keepalived/script/
cd /etc/keepalived/script/
[root@localhost script]# cat redis_check.sh
#!/bin/bash
ALIVE=`/usr/local/redis/bin/redis-cli -a 123456 PING`
if [ "$ALIVE" == "PONG" ]; then
echo $ALIVE
exit 0
else
echo $ALIVE
exit 1
fi
[root@localhost script]# cat redis_master.sh #!/bin/bash REDISCLI="/usr/local/redis/bin/redis-cli -a 123456" LOGFILE="/var/log/keepalived-redis-state.log" echo "[master]" >> $LOGFILE date >> $LOGFILE echo "Being master...." >>$LOGFILE 2>&1 echo "Run SLAVEOF cmd ...">> $LOGFILE $REDISCLI SLAVEOF 172.16.81.140 6379 >>$LOGFILE 2>&1 sleep 10 #延遲10秒之後待數據同步完成後再取消同步狀態 echo "Run SLAVEOF NO ONE cmd ...">> $LOGFILE $REDISCLI SLAVEOF NO ONE >> $LOGFILE 2>&1
[root@localhost script]# cat redis_backup.sh #!/bin/bash REDISCLI="/usr/local/redis/bin/redis-cli -a 123456" LOGFILE="/var/log/keepalived-redis-state.log" echo "[backup]" >> $LOGFILE date >> $LOGFILE echo "Being slave...." >>$LOGFILE 2>&1 sleep 15 #延遲15秒待數據被對方同步完成以後再切換主從角色 echo "Run SLAVEOF cmd ...">> $LOGFILE $REDISCLI SLAVEOF 172.16.81.140 6379 >>$LOGFILE 2>&1
[root@localhost script]# cat redis_fault.sh
#!/bin/bash
LOGFILE=/var/log/keepalived-redis-state.log
echo "[fault]" >> $LOGFILE
date >> $LOGFILE
[root@localhost script]# cat redis_stop.sh
#!/bin/bash
LOGFILE=/var/log/keepalived-redis-state.log
echo "[stop]" >> $LOGFILE
date >> $LOGFILE
三、啓動服務
systemctl start keepalived
systemctl enable keepalived
四、測試服務是否正常
ps -ef | grep keepalived
ping 172.16.81.139
查看VIP地址
測試鏈接redis是否正常
redis-cli -h 172.16.81.139 -p 6379 -a 123456
Keepalived測試完成!!
關閉主redis服務,查看從redis是否會接管VIP變成主?而後再新的主redis141上插入數據,測試當140恢復,數據是否存在?141的是否會變成從節點?
一、主140關閉redis
service redis stop
二、查看141狀態
測試VIP鏈接遠程鏈接
經過INFO能夠查看狀態信息
能夠看到從節點的141已經變成master節點了。
三、插入數據
四、開啓140主節點
service redis start
五、查看140和141的主從狀態
141的狀態,變回了從
140的狀態,變回了主
咱們在140上查看剛剛在141上插入的新數據
數據存在,證實主從切換是正常的!!!
上面是本人親測過的,若有問題請留言!!!