面试问题浓缩总结 面试问题浓缩总结
  • Go
  • Java
  • C/C++
  • JavaScript/HTML
  • MySQL
  • Redis
  • MongoDB
  • 操作系统
  • 计算机网络
  • spring全家桶
  • mybatis
  • 中间件
  • 软件相关
  • 系统相关
  • 算法
  • 数据结构
  • 设计模式
  • CMU硕士经典100题
  • 剑指offer
  • 重点手撕代码
  • 程序员面试金典
  • 3月
  • 4月
  • 智力题
  • 业务问题
  • 一些技术
  • 安全相关
APP下载 (opens new window)
GitHub (opens new window)
  • Go
  • Java
  • C/C++
  • JavaScript/HTML
  • MySQL
  • Redis
  • MongoDB
  • 操作系统
  • 计算机网络
  • spring全家桶
  • mybatis
  • 中间件
  • 软件相关
  • 系统相关
  • 算法
  • 数据结构
  • 设计模式
  • CMU硕士经典100题
  • 剑指offer
  • 重点手撕代码
  • 程序员面试金典
  • 3月
  • 4月
  • 智力题
  • 业务问题
  • 一些技术
  • 安全相关
APP下载 (opens new window)
GitHub (opens new window)
  • MySQL

  • Redis

    • 数据类型
    • 持久化
      • RDB
        • 两种触发方式
        • COW机制
      • AOF
        • 执行流程
      • 恢复
      • 建议
    • 原理
    • 常见问题
    • 分布式锁,过期策略,淘汰规则
    • 集群和限流
    • 面试题
  • MongoDB

  • 数据库
  • Redis
小游
2021-03-20

持久化

包括 RDB 和 AOF 两种机制,下面分别进行说明

# RDB

RDB 持久化机制,是对 Redis 中的数据执行周期性的持久化。更适合做冷备。

优点:

  1. 压缩后的二进制文,适用于备份、全量复制,用于灾难恢复加载RDB恢复数据远快于AOF方式,适合大规模的数据恢复。
  2. 如果业务对数据完整性和一致性要求不高,RDB是很好的选择。数据恢复比AOF快。

缺点:

  1. RDB是周期间隔性的快照文件,数据的完整性和一致性不高,因为RDB可能在最后一次备份时宕机了。
  2. 备份时占用内存,因为Redis 在备份时会独立fork一个子进程,将数据写入到一个临时文件(此时内存中的数据是原来的两倍哦),最后再将临时文件替换之前的备份文件。所以要考虑到大概两倍的数据膨胀性。

# 两种触发方式

  1. SAVE 直接调用 rdbSave ,阻塞 Redis 主进程,导致无法提供服务。
  2. BGSAVE 则 fork 出一个子进程,子进程负责调用 rdbSave ,在保存完成后向主进程发送信号告知完成。在BGSAVE 执行期间仍可以继续处理客户端的请求。

# COW机制

目的是为了解决RDB后台备份时,保证快照是精准的

全称Copy On Write,备份的是开始那个时刻内存中的数据,只复制被修改内存页数据,不是全部内存数据。

缺点: Copy On Write时如果父子进程大量写操作会导致分页错误。

参考:

  1. Redis详解(六)------ RDB 持久化 - YSOcean - 博客园 (cnblogs.com) (opens new window)
  2. Redis-关于RDB的几点顿悟-COW(Copy On Write)_Muscleape的博客-CSDN博客 (opens new window)

# AOF

AOF 机制对每条写入命令作为日志,以 append-only 的模式写入一个日志文件中,因为这个模式是只追加的方式,所以没有任何磁盘寻址的开销,所以很快,有点像 Mysql 中的binlog。AOF更适合做热备。

优点: AOF是一秒一次去通过一个后台的线程fsync操作,数据丢失不用怕。

缺点:

  1. 对于相同数量的数据集而言,AOF文件通常要大于RDB文件。RDB 在恢复大数据集时的速度比 AOF 的恢复速度要快。
  2. 根据同步策略的不同,AOF在运行效率上往往会慢于RDB。总之,每秒同步策略的效率是比较高的。

# 执行流程

  1. 命令的实时写入,不同级别可能有1秒数据损失。命令先追加到aof_buf然后再同步到AO磁盘,如果实时写入磁盘会带来非常高的磁盘IO,影响整体性能。
  2. 对aof文件的重写,目的是为了减少AOF文件的大小,可以自动触发或者手动触发(BGREWRITEAOF),Fork出子进程操作,期间Redis服务仍可用。

流程图如下:

图片

注意事项:

  1. 在重写期间,由于主进程依然在响应命令,为了保证最终备份的完整性;它依然会写入旧的AOF中,如果重写失败,能够保证数据不丢失
  2. 为了把重写期间响应的写入信息也写入到新的文件中,因此也会为子进程保留一个buf,防止新写的file丢失数据
  3. 重写是直接把当前内存的数据生成对应命令,并不需要读取老的AOF文件进行分析、命令合并
  4. 无论是 RDB 还是 AOF 都是先写入一个临时文件,然后通过rename完成文件的替换工作

fork的建议:

  1. 降低fork的频率,比如可以手动来触发RDB生成快照、与AOF重写
  2. 控制Redis最大使用内存,防止fork耗时过长
  3. 合理配置Linux的内存分配策略,避免因为物理内存不足导致fork失败
  4. Redis在执行BGSAVE和BGREWRITEAOF命令时,哈希表的负载因子>=5,而未执行这两个命令时>=1。目的是尽量减少写操作,避免不必要的内存写入操作
  5. 哈希表的扩展因子:哈希表已保存节点数量 / 哈希表大小。因子决定了是否扩展哈希表

# 恢复

启动时会先检查AOF(数据更完整)文件是否存在,如果不存在就尝试加载RDB。

图片

# 建议

既然单独用RDB会丢失很多数据。单独用AOF,数据恢复没RDB来的快,所以出现问题了第一时间用RDB恢复,然后AOF做数据补全。

编辑 (opens new window)
上次更新: 2021/04/01, 17:14:55
数据类型
原理

← 数据类型 原理→

Theme by Vdoing | Copyright © 2021-2021 小游
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式