Redis 持久化
RDB
默认情况下,Redis使用RDB持久化机制,它保存内存数据库快照到dump.rdb的二进制文件中。
在redis.conf中配置RDB持久化触发策略:
# 举例说明,可以配置多个save策略,注释掉所有save策略相当于关闭RDB持久化
save 60 1000 # 表示60秒内有不少于1000个键被修改时触发RDB持久化
也可以手动触发RDB持久化:进入Redis客户端执行save或者bgsave命令
bgsave的写时复制机制
写时复制技术(Copy-On-Write,COW)将复制操作推迟到写操作真正发生的时候,Redis借助操作系统的写时复制技术,做到了在进行RDB持久化生成快照的时候,也可以正常处理写请求。
bgsave的子进程是由主进程fork生成的,可以共享主进程的所有内存数据。bgsave主进程运行后,会读取主进程的内存数据并持久化到RDB文件中。此时,如果主进程对这些数据执行写操作,即将修改的数据会被复制一份,子进程读取副本数据写入RDB文件,而主进程正常修改原来的数据。
AOF(Append Only File)
每次全量保存RDB快照耗时比较长,因此RDB持久化触发间隔不能设置太小,在这个比较长的持久化间隔中,如果Redis宕机,会丢失很多数据。
因此Redis提供了另外一种持久化机制,即AOF,它会将执行的每一条修改命令都记录到{appendfilename} 文件中(appendfilename默认为appendonly.aof)
考虑到效率,实际会先写入os cache,每隔一段时间fsync到磁盘
AOF相关配置
appendonly yes # 打开AOF持久化
# 执行fsync的默认策略为everysec
appendfsync always # 每次有新的命令追加到AOF文件时,就执行一次fsync(持久化非常慢,但是非常安全)
appendfsync everysec # 每秒执行一次fsync(持久化足够快,最多丢失1秒的数据)【默认】
appendfsync no # 交给操作系统判断什么时候执行fsync(持久化非常快,但是非常不安全)
AOF文件一览
以 set Jerry 666
为例:
*3 # 接下来的这条命令由3个部分组成
$3 # 命令的第1个部分有3个字符
set
$5 # 命令的第2个部分有5个字符
Jerry
$3 # 命令的第3个部分有3个字符
666
AOF重写
时间长了,AOF文件中会有很多冗余的命令,因此AOF会定期根据内存最新数据重新生成AOF文件。
会fork一个子进程去执行AOF重写操作
以id为1的文章点赞数为例:
incr article:likes:1
incr article:likes:1
incr article:likes:1
incr article:likes:1
incr article:likes:1
这里5个点赞等价于 set article:likes:1 5
,浪费了很多空间,可以重写为:
*3
$3
set
$15
article:likes:1
$1
5
AOF重写相关配置:
auto-aof-rewrite-min-size 64mb # AOF文件自动重写需要达到的大小
auto-aof-rewrite-percentage 100 # 上次重写后,下次重写需要AOF文件大小增长的百分比
RDB和AOF对比
由于宕机时AOF丢数据较少,当Redis重启时,会优先使用AOF文件重建内存数据,其次使用RDB文件。
混合持久化
Redis 4版本开始,吸取RDB和AOF两种持久化方式的优点,新增了一个持久化方式:混合持久化。
通过 aof-use-rdb-preamble yes
配置开启混合持久化,本质上混合持久化是对AOF的优化,因此也必须开启AOF。
如果开启了混合持久化,Redis在重写AOF时,会将重写这一时刻之前的内存数据保存为RDB快照,而重写之后新增的命令以AOF的方式追加写入。
使用混合持久化之后,Redis重建内存数据时,会先使用RDB数据重建大部分数据,再使用AOF数据重建最后的小部分数据,重建速度得以大大提升。
在Redis 7版本之前,RDB快照数据和增量AOF数据都保存在{appendfilename}文件中(appendfilename默认为appendonly.aof),从7版本开始,RDB快照数据保存到 {appendfilename}.{序号}.base.rdb 中, 增量AOF数据保存到{appendfilename}.{序号}.incr.aof中
Redis持久化数据备份策略
例如,可以使用crontab定时脚本:
每小时复制一份RDB或AOF文件到一个指定目录,仅保留48小时的备份
每一天复制一份RDB或AOF文件到一个指定目录,仅保留30天的备份
每天晚上将当前机器的备份数据复制到其他机器上