深入理解Redis系列——持久化机制详解

RDB持久化

Redis是内存数据库,它将自己的数据存储在内存当中,所以当计算机关机,或者redis退出,就会导致数据丢失,所以需要把数据保存到磁盘上。

RDB就是一种持久化方式。

有两个命令用于生成RDB文件,SAVE和BGSAVE,两者的不同点在于SAVE是将redis进程阻塞后进行保存,BGSAVE是创建出一个子进程完成RDB文件的保存,父进程可以继续处理请求命令。

执行BGSAVE期间,客户端给服务器发送的SAVE, BGSAVE, BGREWRITEAOF命令都不能执行。

BGSAVE的执行可由配置文件设置,比如:、

在redisServer结构中有一个dirty字段记录着从上一次save命令执行后到现在数据库发生了多少次修改,lastsave字段记录着上一次执行save命令的时间。

然后函数serverCron每隔100ms检查一下那两个字段判断是否满足设置的保存条件。

RDB文件是一个经过压缩的二进制文件,由多个部分组成。

对于不同类型的键值对,RDB文件会使用不同的方式来保存它们。

在服务器启动的时候,如果同时存在RDB文件和AOF文件,会优先使用AOF文件还原数据库。

AOF持久化

除了RDB持久化功能之外,Redis还提供了AOF (Append Only File)持久化功能。与RDB持久化通过保存数据库中的键值对来记录数据库状态不同,AOF持久化是通过保存Redis 服务器所执行的写命令来记录数据库状态的。

载入的时候通过再执行这些写指令来恢复数据库状态。

AOF文件的写入和同步

AOF文件的写入与同步时,对于flushAppendOnlyFile函数,它就是实现持久化的函数,把内存中数据写入文件,这个函数的行为是由服务器配置的appendfsync选项的值(如下图)来决定的。

写命令会先写入到一个缓冲区中,然后再写入AOF文件(这时候在内存缓冲区中),然后通过设置参数决定缓冲区的内容同步到AOF文件中。

我们可以看到三个值都是将aof_buf缓冲区的所有内容写入到aof文件,只是同步时操作不一样。对此,我们来理解一下写入和同步!

解答:

在现代os中,为了提高文件的写入操作,当用户调用到write函数将数据写入文件时,os先将数据写入到一个内存缓冲区里,正常是等到缓冲区满了或是规定时间到了,才真正地将缓冲区里的数据写入磁盘,这时才是持久化完成。

类似你用记事本写东西一样,写完之后你会Ctrl+s(保存),但是在没执行Ctrl+s的时候你也能看到自己写的,这时因为保存在内存缓冲区里了,然后你保存了,这才保存到磁盘了,所以我们可以把你写东西当做是对aof文件的写入,你执行Ctrl+s才是同步到磁盘操作。

这样虽然大大提高了效率,但是很不安全,在你写了好多字时,卡,忽然电脑停机了,写的东西全没了,就问你气不气?

所以appendfsync的选项值中的always、everysec都可以强制让os立即将缓冲区里的数据写入硬盘。always是写到缓冲区了立马就同步到磁盘,everysec是写到缓冲区的数据每秒就同步一次,丢失了也就丢失了上一秒内的数据,也不是很气。

Always是安全性最高的,但效率差;everysec最多丢失一秒钟的数据,足够快;no是最快的,但可能会丢失很多的数据。

AOF文件的载入和还原

因为redis命令只能在客户端中执行,所以redis服务器在执行AOF文件中命令的写入前,先会创建一个伪客户端,然后执行每条指令。

AOF重写

因为写命令越来越多,AOF的文件体积可能越来越大,对计算机,redis服务器也会造成巨大影响,并且数据还原的时间也就很长。

为了解决体积膨胀的问题,Redis会使用新的AOF文件代替原AOF文件,但新AOF文件不会包含冗余的指令,使得体积得以缩小。

实际上,新AOF文件并不是通过分析原文件来进行重写指令的,而是通过读取当前数据库状态来实现的。

如果服务器想要用尽量少的命令来记录list键的状态,那么最简单高效的办法不是去读取和分析现有AOF 文件的内容,而是直接从数据库中读取键list的值,然后用一条RPUSH list "C" "D""E""F”"G"命令来代替保存在AOF文件中的六条命令,这样就可以将保存list键所需的命令从六条减少为一条了。

AOF重写是在后台进行的,因为不想阻塞父服务器继续处理请求,所以创建了一个子进程去执行重写,子进程中有父进程数据库状态的拷贝,但子进程在重写过程中,可以父进程又有新的写命令使得数据库状态发生了改变,可能造成数据库状态和AOF文件的不一致问题,所以Redis服务器设置了一个AOF重写缓冲区,存放这一期间的写命令。所以实际上父进程执行这段时间的写命令是将写命令追加到AOF缓冲区和AOF重写缓冲区

然后在子进程完成重写后,再去执行AOF重写缓冲区中的命令。最后用新的AOF文件替换旧的AOF文件。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值