Redis持久化与复制
持久化
Redis提供了两种不同的持久化方法来将数据存储到硬盘。快照(snapshoting)以及只追加文件(AOF)。这两种持久化方法既可以同时使用,又可以单独使用。
1. 快照持久化(snapshoting)
Redis通过创建快照来获得存储在内存里的数据在某个时间点上的副本。
在快照创建完成之后,用户可以对快照进行备份。
创建快照的方式有
- 客户端可以通过向redis发送
BGSAVE
命令来创建一个快照。执行这个命令后,redis会创建一个子进程,然后子进程负责将快照写入到磁盘,而父进程继续处理命令请求。 - 客户端可以通过向redis发送
SAVE
命令来创建一个快照。redis接到SAVE
命令后,在快照创建完之前就不会再响应其他命令了。这个命令很少用,一般是内存不够创建子进程或者其他空余时间才会使用。 - 如果
SAVE
命令设置了配置选项,比如SAVE 60 10000
,当60秒内有10000次写入,这个条件被出发时,就会自动触发BGSAVE
命令。 - 当redis通过
SHUTDOWN
命令接收到关闭服务器请求时,或者接收到标准TERM
信号时,会执行一个SAVE命令,完成后关闭服务器。 - 当一个redis连接另一个redis服务器。并向对方发送
SYNC
命令开始一次复制操作的时候,那么主服务器就会执行一次BGSAVE
命令。
快照持久化的使用场景
- 对日志进行聚合计算
在日志文件进行聚合计算或者对页面浏览量进行分析的时候,我们只需要考虑:如果redis因为崩溃而未能成为创建新的快照,那么我们能够承受丢失多久时间内的数据。如果一小时内的数据可以被接受,那么使用配置值save 3600 1
。在觉得好持久化配置后,就需要解决如果恢复因为故障中断的日志处理操作。把日志的处理进度记录到redis中,在系统崩溃后,根据进度记录继续执行之前的工作。 - 大数据
当redis存储的数据越来越多以后,BASAVE在创建子进程时的消耗也会越来越多。为了防止redis创建子进程而停顿,可以使用SAVE命令
2. AOF持久化
当程序无法接受一定时间的数据丢失时,可以使用AOF持久化。
AOF持久化会将被执行的命令写到AOF文件的末尾,以此来记录数据的变化。所以redis只要重新执行以此AOF文件的命令,就可以恢复AOF文件所记录的数据。
AOF持久化可以在redis.config文件中修改配置appendonly yes
来开启。修改配置appendfsync
的选项来改变AOF状态
- always: 每个redis命令都同步写入,这会严重降低redis的速度
- everysec: 每秒执行一次同步
- no: 让操作系统来决定什么时候同步
重写/压缩AOF文件
虽然AOF非常灵活的提供了多个选项来满足不同应用程序的需求,但是AOF持久化也有缺陷,就是AOF文件的体积大小
随着redis不断运行,AOF文件的体积也在不断增大。这会导致redis还原数据时要执行的AOF文件庞大,耗时很长。
为了解决AOF文件体积不断增大的问题,可以在客户端使用BGREWRITEAIF
命令,它会移除AOF文件中的冗余命令来重写AOF文件,它和BGSAVE
类似,也会创建子进程来工作。但这又造成了和快照方式相同的问题,甚至更糟糕,因为移除AOF文件时,可能导致系统长时间挂起。
AOF持久化也可以设置auto-aof-rewrite-percentage选项和auto-aof-rewrite-min-size选项,来自动执行BGREWRITEAIF,如果重写过于频繁,可以将percentage设置到100以上,比上次文件扩大一倍以上时才触发重写。
无论是AOF还是快照,都可以将数据持久化到硬盘,但除了持久化,用户还必须对持久化文件进行备份
复制
复制可以让其他服务器拥有一个不断更新的数据副本,从而使得其他服务器可以用于处理客户端发送的读请求。
关系型数据库通常会使用一个主服务器向多个从服务器发送更新,并使用从服务器来处理读请求。redis也采用了相同的方法来实现。来扩展读请求。
1. Redis主从复制的过程
- 主服务器等待命令,从服务器连接主服务器,发送SYNC命令。
- 主服务器开始执行BGSAVE,并用缓冲区记录BGSAVE之后的命令。从服务器根据配置决定继续使用现有数据处理客户端请求,还是返回错误。
- BGSAVE执行完毕,向从服务器发送快照文件,并在发送期间继续记录命令到缓冲区。 从服务器丢弃旧数据,开始载入主服务器发送的快照文件。
- 快照文件发送完毕,开始向从服务器发送缓冲区中的命令。从服务器完成快照文件的加载,开始接受请求命令。
- 缓冲区存储命令发送完毕,然后每执行一个请求同时就向从服务器发送相同的的命令。 从服务器执行主服务器缓冲区发送的写命令,并执行每个主服务器发送的写命令。
2. 如何配置
配置从服务器很简单, 只需要在从服务器的slave配置文件中加入slave 192.168.1.1 9999
3. Redis主从链
当Redis出现一主多从的情况时,可能会导致网络资源不够用。
犹豫redis主服务器和从服务器并没有特别不同的地方,所以从服务器也可以拥有自己的从服务器。组成主从链。
4. 哨兵模式
Redis主从复制会存在一个问题,就是当主机宕机时就会发生群龙无首的情况。
所以要做的事情就是从从机中选出一个来作为新的主机。
- Redis使用哨兵来监控服务,Sentinel会作为一个独立的进程,通过向redis发送命令,等待redis响应来监控多个redis服务。
- 当哨兵检测到master宕机后,会通知其他哨兵来与master通信,如果其他哨兵认为此master以及宕机的数量超过一定值, 哨兵就会让master下线。
- 然后会进行slave作为master的选举,每个sentinel对监控的slave进行优先级计算(主要观察slave的健康状态),排序后, 选择优先级最高的slave,执行
slaveof no one
作为新master。 - 然后通知其他服务器,修改配置,切换主机,并且监控老的master,如果恢复,使其成为新master的slave。
一个问题 单机时,客户端可以直接连接主服务器。但是主从集群时,如果主服务器变更,客户端如何知晓呢??
在使用主从服务哨兵模式时,客户端不能直接连接到redis集群。而是连接到哨兵集群,通过哨兵节点来获取redis主节点。