前言
redis是一款k/v类型的nosql存储系统,类似于memcache,所有的数据都存储在内存中,所以读写性能非常好。不过redis和memcache还是有区别的,redis的性能相对于memcache更高,而且redis支持更多的数据类型(string、hash(关联数组)、set(集合)、有序集合、list等)。而且redis支持数据的持久性,可以定期把内存中的数据保存到磁盘。redis通过sentinel组件还可以实现主从复制,而memcache要实现此功能只能借助于客户端的双写操作。
sentinel介绍
sentinel即哨兵的意思,其可以让redis实现主从复制,当一个集群中的master失效之后,sentinel可以选举出一个新的master用于自动接替master的工作,集群中的其他redis服务器自动指向新的master同步数据。一般建议sentinel采取奇数台,防止某一台sentinel无法连接到master导致误切换。其结构如下:
实验配置
实验拓扑如下:
三台服务器,分别担任redis和sentinel的角色,其中一台为master,另外两台为slave。master发生故障时由三台sentinel选举出新的master。
主从配置实验步骤
- 安装redis,安装完redis后sentinel也会随着redis自动安装上。redis监听在6379端口,sentinel监听在26379端口。
yum install -y redis
- 配置redis主从复制,配置文件为/etc/redis.conf,开启数据持久化操作。
bind 0.0.0.0 #监听在本地所有ip#
appendonly yes #开启aof持久化#
slaveof 192.168.11.197 6379 #slave需要配置此选项,master不需要配置,表示指定192.168.11.197为主节点#
slave-read-only yes #从节点只读,master可读可写#
- 查看主从复制是否配置成功:
[root@localhost ~]# redis-cli #在master执行如下命令登录到redis控制台#
127.0.0.1:6379> info replication #查看复制集群信息#
# Replication
role:master #当前角色为master#
connected_slaves:2 #一共有两个slave#
slave0:ip=192.168.11.198,port=6379,state=online,offset=43,lag=0 #slave的ip#
slave1:ip=192.168.11.199,port=6379,state=online,offset=43,lag=1
master_repl_offset:43
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:2
repl_backlog_histlen:42
-
master新增一个key,slave也可以查到该key
master:
slave:
slave添加key则报错,如下:
sentinel配置实验步骤
-
sentinel随着redis一块会安装到系统上,配置文件为/etc/redis-sentinel.conf,修改三台服务器的配置文件如下:
#监听端口# port 26379 #工作目录# dir /tmp #监控的master和端口# sentinel monitor mymaster 192.168.11.197 6379 2 #多长时间联系不到master则触发选举# sentinel down-after-milliseconds mymaster 30000 #在failover过程中,能够被新master同时配置的slave数量# #此值较大意味着集群无法响应客户端的时间较长# #此值较小意味着同时还能有slave用旧数据响应客户端请求# sentinel parallel-syncs mymaster 1 #failover转移时间,超出此时间认为master转移失效,重新开始转移# sentinel failover-timeout mymaster 180000 #sentinel日志文件# logfile /var/log/redis/sentinel.log
-
配置完成之后直接启动redis-sentinel服务即可,此服务会监听在26379端口。
-
在master同过如下命令可以查看sentinel集群的状态:
[root@localhost ~]# redis-cli -p 26379
#查看master状态#
127.0.0.1:26379> sentinel masters mymaster
#查看slave状态#
127.0.0.1:26379> sentinel slaves mymaster
#手动执行故障转移#
127.0.0.1:26379> sentinel failover mymaster
#查看指定sentinel集群#
127.0.0.1:26379> sentinel get-master-addr-by-name mymaster
- 默认master是192.168.11.197,此时如下命令:
127.0.0.1:26379> sentinel failover mymaster
OK
127.0.0.1:26379> sentinel get-master-addr-by-name mymaster
1) "192.168.11.198"
2) "6379"
可以看到master已经转移到192.168.11.198上去了。
- 查看/etc/redis-sentinel.conf配置文件可以看到多了如下几行:
192.168.11.197:
192.168.11.198:
可以看到其实master转移就是通过自动修改配置文件来实现的,而且以前的master成为slave之后也将成为只读状态。
redis的持久化
此处补充一些redis的持久化的内容,redis有两种方式来实现数据的持久化,一种是通过RDB,一种是通过AOF,分别介绍两种配置
RDB
RDB是通过快照方式进行持久化,即按照实现配置好的策略,当达到策略要求的时候就会自动触发快照,然后在redis数据目录下保存一个dump.rdb格式的文件。客户端也可以显示使用save和bgsave命令进行快照保存,不过save是同步方式,会阻塞客户端请求,bgsave为异步方式,不会阻塞客户端请求。
配置文件如下:
save 900 1 #900秒内数据发生一次变化则触发快照#
save 300 10 #300秒内数据发生10次变化则触发快照#
save 60 10000 #60秒内数据发生10000此变化则触发快照#
stop-writes-on-bgsave-error yes #当快照保存有错误是停止响应客户端操作#
rdbcompression yes #启用rdb文件压缩保存#
rdbchecksum yes #开启rdb文件校验#
dbfilename "dump.rdb" #保存文件名#
dir "/var/lib/redis" #保存路径#
AOF
AOF为只追加文件的意思,RDB只能保存快照当前的状态,还是会丢失数据。但是AOF表示当数据发生改变则直接保存到磁盘,基本不会发生数据丢失,其保存频率可以通过配置文件来控制,同时也可以通过执行bgrewriteof显示触发rewrite操作。
appendonly no #是否开启aof,默认没有开启#
appendfilename "appendonly.aof" #aof保存文件名#
#aof主动同步保存频率#
# appendfsync always #当发生数据变化则保存#
appendfsync everysec #每秒保存#
# appendfsync no #数据首先写入缓存,由系统内核决定何时写入文件#
no-appendfsync-on-rewrite no #是否在后台执行aof重写期间不调用fsync,no表示调用#
#aof-rewrite触发条件,rewrite表示重新生成一个新的aof文件,此方法有助于数据恢复速度。此处两个条件需要同时满足才能触发rewrite#
auto-aof-rewrite-percentage 100 #当前相对于前一个aof文件数据发生100%变化则触发#
auto-aof-rewrite-min-size 64mb #数据变化量不小于64M则触发#
aof-load-truncated yes #是否启用truncated#
注意:
BGSAVE和BGREWRITEAOF不会同时进行;
Redis服务器启动时用持久化的数据文件恢复数据,会优先使用AOF;
数据持久机制并不能代替备份,所以还需要对redis数据做好备份操作;
总结
sentinel从一定程度上确实解决了redis主从复制的问题。不过问题是只有master可读可写,从节点只读,从一定程度上提高了读性能,但是写性能还是有瓶颈。不过redis3.2已经支持了另外一套集群方案(redis cluster),所有redis服务器通过slots来进行数据的分布式存储,都是可读可写的状态,所以不再有中心节点(master),可以说是真正实现了分布式集群。