欢迎来到尧图网

客户服务 关于我们

您的位置:首页 > 健康 > 养生 > Redis 持久化详解

Redis 持久化详解

2024/11/30 8:35:37 来源:https://blog.csdn.net/m0_72397750/article/details/140619208  浏览:    关键词:Redis 持久化详解

AOF 持久化

AOF持久化数据恢复相对RDB慢,文件也更大,但数据丢失的风险更小。

AOF 写入

将数据写入Redis内存后,将写数据的命令记录到AOP磁盘文件。

【结构】server.aof_buf

主线程写操作执行完之后,命令会先追加到 Redis 的 server.aof_buf 缓冲区。

【方法】write()

将 server.aof_buf 内的数据写入操作系统内核的文件缓冲区 page cache。(此时还没有写入到硬盘)

【参数】appendfsync

设置AOF刷盘策略。

  • Always:每次写操作命令执行完后,不仅过文件缓冲区,直接同步将 AOF 日志数据写回硬盘;
  • Everysec:每次写操作命令执行完后,先将命令写入到 AOF 文件的内核缓冲区,然后每隔一秒将缓冲区里的内容写回到硬盘;
  • No:意味着不由 Redis 控制写回硬盘的时机,转交给操作系统控制写回的时机,也就是每次写操作命令执行完后,先将命令写入到 AOF 文件的内核缓冲区,再由操作系统决定何时将缓冲区内容写回硬盘。

Redis2.6 追加了 lazyfree 线程,先将AOF刷盘任务存在阻塞队列 BIO_AOF_FSYNC,由后台线程逐步完成。

AOF 重写

【参数】auto-aof-rewrite-min-size

由于AOF是以追加命令的方式记录的,文件大小达到阈值时需要进行AOF重写来缩小文件体积。

【方法】folk()

主进程调用 folk() 方法生成 bgrewriteaof 子线程重写AOF文件,具体就是逐一把内存数据的键值对转换成一条命令,再将命令记录到重写日志,誊录完覆盖原有的AOF日志。

子进程与主进程共享内存,且对内存只进行读操作。如果父子进程在重写过程中修改了数据,会发生写时复制,进程之间有独立的数据副本,会先复制一份物理内存,不需要加锁来保证数据安全。

【结构】重写缓冲区

AOF重写期间主进程执行的新命令由于独立的数据副本不会抄录到AOF中,主进程会先存在重写缓存区中。

这期间主进程的工作包括:执行客户端的命令,将执行后的命令写到AOF缓冲区以及AOF重写缓冲区。

AOF重写完成后,会向主进程发送信号,这时主进程会将重写缓冲区内的数据写入AOF,并将新的AOF文件替换原来的。(注意此时如果重写缓冲区数据较多可能会阻塞主进程

RDB持久化

内存数据的全量快照,加载比较快,数据量也更小,但由于是全量,不可能像AOF一样秒级存储,相对来说RDB丢失数据的风险更大。

生成RDB文件

【命令】save 主线程同步生成RDB文件

【命令】bgsave 创建子进程来生成RDB文件,避免阻塞。

【参数】save 300 10 300 秒之内,对数据库进行了至少 10 次修改。

bgsave的子进程赋值数据与AOF重写是类似的,主进程要修改此时共享的内存里的数据,发生写时复制,这块物理内存会被复制一份,主进程在数据副本中操作,子进程还是把原有的数据进行快照保存。

但RDB不想AOF会有重写缓冲区来抄录这段时间产生的新数据,在下次RDB文件抄录前如果发生崩溃,数据将会丢失

写时复制的存在,极端情况下,会使得内存占用为原来的2倍。且写时复制需要由主进程来复制一份数据副本,如果是大key,将可能阻塞主进程。

RDB和AOF混合持久化

AOF重写时和RDB很像,是全量数据保存(只不过RDB保存的数据,AOF保存的是命令),可以采用混合持久化。

【参数】aof-use-rdb-preamble yes

用于开启混合持久化。

原先抄录内存中所有的数据转为命令保存到AOF文件的操作变为用RDB快照写入AOF,这期间主进程执行的写操作产生的新数据依旧会存在重写缓冲区内,以增量数据的形式填充到AOF,再替换旧的AOF文件。

这样重启时数据加载会很快,数据丢失的也更少。

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com