Redis持久化
一、Redis为什么要做持久化?
redis数据存放在内存中,redis挂掉或重启,数据都会消失,开启持久化可以在重新启动或恢复数据。
二、Redis的两种持久化方式:RDB快照和AOF。
Redis4.0之后新增混合持久化,即在AOF文件在重写是使用RDB的二进制方式存储数据。
1、RDB快照
redis默认把文件保存在dump.rdb文件中
save N M //在N秒内至少有M个改动,就会保存一次RDB
save 60 10000 //在60s之内对redis的操作的改动有10000次,redis就会把内存的所有数据写在dump.rdb文件中
上面配置用来配置RDB快照执行规则,在redis.conf中配置。
关闭RDB只需将所有的save保存策略注释即可。
也可以手动使用命令生成RDB快照,在redis客户端执行命令 save或bgsave即可。
每次命令执行都会将所有的redis内存快照到一个新的dump.rdb中,并覆盖原来的文件。
save 和bgsave的区别:
1)save是同步操作,执行save命令是会阻塞客户端其他redis命令;bgsave是异步的,不会阻塞客户端其他redis命令。
2)bgsave需要fork子进程,会消耗内存,而save操作不会消耗内存。
配置中自动生成rdb文件后台使用的是bgsave方式。
2、AOF(append-only file)
如何开启AOF持久化?
在redis.conf文件中配置appendonly yes 即可开启AOF持久化
AOF持久化,即将修改的每一条指令记录进文件。redis每执行一个改动命令,这个命令就会被追加到AOF文件的末尾。使用AOF恢复数据,就是将aof文件中的命令逐一执行。
可以在redis.conf中配置多久将数据fsync到磁盘中一次。
1)appendfsync always //每次有新命令,就执行一次
2)appendfsync everysec // 每秒fsync一次
3)appendfsync no //从不fsync
第一种方式很安全但很慢,第二种方式足够快,但又可能会在发生故障时丢失1秒钟的数据。
AOF重写
aof文件有很多类似incr等计数类似的无用指令,所以AOF会定期根据内存的最新数据重写aof文件
redis.conf中两个aof重写配置
1)auto-aof-rewrite-min-size 64mb //aof文件至少要达到64m才会自动重写,文件太小恢复速度很快,重写意义不大
2)auto-aof-rewrite-percentage 100 //aof文件自上一次重写后文件增长一倍100%才会再次触发重写。
手动重写
进入客户端执行命令bgrewriteaof重写AOF
AOF重写redis会fork出一个子进程去做(与bgsave类似),不会影响redis的其他命令执行
3、redis4.0的混合持久化
redis重启时,执行aof文件恢复数据需要很长时间,redis4.0为了解决这个问题,带来了一个新的特性--混合持久化。
通过 aof-use-rdb-preamble yes 开启混合持久化 ,混合持久化必需在aof开启的前提下开启。
开启混合持久化后,aof在重写的时候,不再单纯的将内存数据转换为resp命令写入aof文件,而是将重写这一刻的内存做RDB快照存储在aof文件中。并将RDB快照内容和增量修改AOF修改内存数据命令存放在一起,都写入AOF文件中。
于是在redis重启时,先加载RDB内容,然后执行增量的aof日志,这样重启的效率就会得到大幅度提升。
三、Redis数据备份
1、写个定时脚本,每小时copy一分rdb或aof文件到一个目录中去,保留48小时的备份
2、每天保留一份当日的数据备份到一个目录中去,可以保留进一个月的备份,想要恢复哪天的数据,都可以。
3、每天晚上将当前机器上的备份到其他机器一份,以防机器损坏。
bgsave的写时复制
执行bgsave命令时,由redis主线程fork出一个子线程执行,子线程可以共享主线程的所有内存数据,bgsave子线程读取主线程内存数据,并把它们写入RDB文件中,此时如果主线程要改动数据,那么这块数据会被复制一份,生成该数据的副本,然后bgsave子进程会把这个副本数据写入RDB文件中。