Redis之RDB持久化
定义
- RDB 是 Redis 将 server 端的内存中的键值对以二进制的方式,持久化存储的一种文件形式。 文件中,一般会以
对象的长度+对象
的格式来存储,只要根据这个格式,就能渐进的遍历整个文件。 - Redis 还支持开启 LZF 的压缩算法,可以牺牲 CPU 时间,来减少 RDB 文件的大小;如果开启LZF并且超过20个 bytes 时, 会将压缩后的字符写入文件。
触发方式
自动触发
Redis通过配置save参数,来触发RDB持久化条件。
默认如下配置:
1 | save 900 1:表示900 秒内如果至少有 1 个 key 的值变化,则保存 |
手动触发
提供了两种命令
- save
该命令会阻塞当前Redis服务器,执行save命令期间,Redis不能处理其他命令,直到RDB过程完成为止。 - bgsave
执行该命令时,Redis会在后台异步进行快照操作,同时还可以响应客户端请求。具体操作是Redis进程执行fork操作创建子进程,RDB持久化过程由子进程负责,完成后自动结束。阻塞只发生在fork阶段,一般时间很短。
对比
恢复数据
- 将备份文件 (dump.rdb) 移动到 redis 安装目录并启动服务即可,redis就会自动加载文件数据至内存了。
- Redis 服务器在载入 RDB 文件期间,会一直处于阻塞状态,直到载入工作完成为止。
注:获取 redis 的安装目录可以使用 config get dir 命令
停止持久化
当只想利用Redis的缓存功能,并不像使用 Redis 的持久化功能, 可以将redis.conf 中,save 行注释掉或者直接一个空字符串save ""
, 来停用保存功能
RDB自动保存原理
redisService结构
Redis的服务器状态,使用redisService结构保存
1 | struct redisService{ |
举例:
在 redis.conf 配置文件中进行了关于save 的配置,在服务器状态中的saveparam 数组将会是如下的样子:
dirty 计数器和lastsave 属性
dirty 计数器: 记录距离上一次成功执行 save 命令或者 bgsave 命令之后,Redis服务器进行了多少次修改(包括写入、删除、更新等操作)。
lastsave 属性: 它是一个时间戳,记录上一次成功执行 save 命令或者 bgsave 命令的时间。
- 通过这两个命令,当服务器成功执行一次修改操作,那么dirty 计数器就会加 1,而lastsave 属性记录上一次执行save或bgsave的时间。
- Redis 服务器还有一个周期性操作函数 severCron ,默认每隔
100 毫秒
就会执行一次,该函数会遍历并检查 saveparams 数组中的所有保存条件,只要有一个条件被满足,那么就会执行 bgsave 命令。- 执行完成之后,dirty 计数器更新为 0 ,lastsave 也更新为执行命令的完成时间。
RDB文件结构
- 简要
- 详解
下面是一个 version 9 的 RDB 文件
注:RDB文件保存的是二进制数据。
REDIS部分
作用:RDB文件标识符。通过这五个字符,程序可以在载入文件时,快速检查所载入的文件是否为RDB文件
长度:5字节,保存REDIS这五个字符
db_version部分
作用: 代表RDB文件的版本号。
长度:4字节,值是一个字符串表示的整数
databases部分
作用:包含0或多个数据库及其对应的键值对数据
长度:如果服务器数据库状态为空,则为0;如果不为空,则根据键值对的数量、类型和内容,长度也随之而变
EOF部分
作用:RDB文件结束符。标志着RDB文件正文内容的结束,读入程序遇到这个值时,代表所有数据库的所有键值对都载入完毕了
长度:1字节
check_sum部分
作用:检查RDB文件是否有出错或损坏。是程序通过对REDIS、db_version、databases、EOF四个部分的内容进行计算而出的;载入RDB文件时,会将载入数据所计算出的校验和与check_sum进行对比,从而得出是否出错
长度:8字节的无符号整数
优势与劣势
优势
- 它保存了redis 在某个时间点上的数据集。这种文件非常适合用于进行备份和灾难恢复。
- RDB 在恢复大数据集时的速度比 AOF 的恢复速度要快。
劣势
- 影响性能: RDB方式数据没办法做到实时持久化/秒级持久化。因为bgsave每次运行都要执行fork操作创建子进程,属于重量级操作(内存中的数据被克隆了一份,大致2倍的膨胀性需要考虑),频繁执行成本过高。
- 版本不兼容: RDB文件使用特定二进制格式保存,Redis版本演进过程中有多个格式的RDB版本,存在老版本Redis服务无法兼容新版RDB格式的问题。
- 数据有丢失: 在一定间隔时间做一次备份,所以如果redis意外down掉的话,就会丢失最后一次快照后的所有修改。
相关配置
1 | # RDB自动持久化规则 |
参考:
https://segmentfault.com/a/1190000020518214 >https://blog.csdn.net/qq_41594698/article/details/94902254