Redis 持久化

文章目录

1.RDB 快照

RDB(Redis Database)指定时全量快照持久化。

有两个 Redis 命令可用于生成 RDB 文件,一个是 SAVE,另一个是 BGSAVE。

  • SAVE:生成 RDB 快照文件,但是会阻塞主进程,服务器将无法处理客户端发来的命令请求,所以通常不会直接使用该命令。
  • BGSAVE:fork 子进程来生成 RDB 快照文件,阻塞只会发生在 fork 子进程的时候,之后主进程可以正常处理请求

可以手动触发 SAVE 与 BGSAVE 命令。

也可以使用 save point 配置,满足 save point 条件后会自动触发 BGSAVE 来存储一次快照。

save point 格式:save <seconds> <changes>,含义是 Redis 如果在 seconds 秒内数据发生了 changes 次改变,就保存快照文件。例如 Redis 默认配置了以下 3 个:

save 900 1 		# 900秒内有1个key发生了变化,则触发保存RDB文件
save 300 10 	# 300秒内有10个key发生了变化,则触发保存RDB文件
save 60 10000	# 60秒内有10000个key发生了变化,则触发保存RDB文件

其优点:

  • 相对于 AOF,RDB 文件体积更小(二进制 + 压缩)
  • 在恢复大数据集时,RDB 比 AOF 更快

其缺点:

  • 不够及时,可能会发生数据丢失。
  • 对于大数据集,生成快照可能会导致主进程阻塞。

工作原理:

  • Redis 调用 fork(),产生一个子进程。
  • 子进程把二进制数据写到一个临时的 RDB 文件。
  • 当子进程写完新的 RDB 文件后,把旧的 RDB 文件替换掉。

2.AOF 日志

AOF(Append-Only File)指持续增量持久化,记录每一次写命令。

AOF 持久化支持不同的同步方式,通过配置 appendfsync 来设置:

  • appendfsync always:主线程同步。很慢,但是很安全。
  • appendfsync everysec:后台线程每间隔 1 秒同步。折中方案。
  • appendfsync no:由 OS 同步。很快,但不安全。

一般情况下都采用 everysec 配置,这样可以兼顾速度与安全,最多损失 1s 的数据。

AOF 解决了数据实时持久化,但我们还会面临另一个问题,数据实时写入 AOF,随着时间的推移,AOF 文件会越来越大,那使用 AOF 恢复时变得非常慢,这该怎么办?

Redis 贴心地提供了 AOF rewrite 方案,俗称「AOF 瘦身」,顾名思义,就是压缩 AOF 的体积。

因为 AOF 里记录的都是每一次写命令,例如执行 set k v1,set k v2,其实我们只关心数据的最终版本 v2 就可以了。AOF rewrite 正是利用了这个特点,在 AOF 体积越来越大时(超过设定阈值),Redis 就会定期重写一份新的 AOF,这个新的 AOF 只记录数据的最终版本就可以了。

3.混合持久化

Redis 4.0 以上版本支持混合持久化。

混合持久化本质是通过 AOF 后台重写(bgrewriteaof 命令)完成的,不同的是当开启混合持久化时,fork 出的子进程先将当前全量数据以 RDB 方式写入新的 AOF 文件,然后再将 AOF 重写缓冲区(aof_rewrite_buf_blocks)的增量命令以 AOF 方式写入到文件,写入完成后通知主进程将新的含有 RDB 格式和 AOF 格式的 AOF 文件替换旧的 AOF 文件。

简单来说,当 AOF 在做 rewrite 时,Redis 先以 RDB 格式在 AOF 文件中写入一个数据快照,再把在这期间产生的每一个写命令,追加到 AOF 文件中。

注意:混合持久化是对 AOF rewrite 的优化,这意味着使用它必须基于 AOF + AOF rewrite。

4.从持久化中恢复数据

数据的备份、持久化做完了,我们如何从这些持久化文件中恢复数据呢?

如果一台服务器上有既有 RDB 文件,又有 AOF 文件,该加载谁呢?

其实想要从这些文件中恢复数据,只需要重新启动 Redis 即可。我们还是通过图来了解这个流程:

启动时会先检查 AOF 文件是否存在,如果不存在就尝试加载 RDB。

那么为什么会优先加载AOF呢?因为AOF保存的数据更完整,通过上面的分析我们知道 AOF 基本上最多损失 1s 的数据。


参考文献

AOF 持久化是怎么实现的?- 小林 coding
Redis专题:万字长文详解持久化原理
面试必问的Redis:RDB、AOF、混合持久化 - 知乎

相关推荐
Dlwyz3 小时前
redis-击穿、穿透、雪崩
数据库·redis·缓存
工业甲酰苯胺5 小时前
Redis性能优化的18招
数据库·redis·性能优化
Oak Zhang8 小时前
sharding-jdbc自定义分片算法,表对应关系存储在mysql中,缓存到redis或者本地
redis·mysql·缓存
门牙咬脆骨8 小时前
【Redis】redis缓存击穿,缓存雪崩,缓存穿透
数据库·redis·缓存
门牙咬脆骨8 小时前
【Redis】GEO数据结构
数据库·redis·缓存
墨鸦_Cormorant10 小时前
使用docker快速部署Nginx、Redis、MySQL、Tomcat以及制作镜像
redis·nginx·docker
Dlwyz13 小时前
问题: redis-高并发场景下如何保证缓存数据与数据库的最终一致性
数据库·redis·缓存
飞升不如收破烂~14 小时前
redis的List底层数据结构 分别什么时候使用双向链表(Doubly Linked List)和压缩列表(ZipList)
redis
吴半杯15 小时前
Redis-monitor安装与配置
数据库·redis·缓存
会code的厨子17 小时前
Redis缓存高可用集群
redis·缓存