好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

Redis设计与实现 第 10 章 RDB 持久化

第 10 章 RDB 持久化

数据库状态:服务器中的非空数据库以及它们的键值对统称为数据库状态

Redis 提供 RDB 持久化功能,将内存中的数据库状态保存到磁盘中,避免数据意外丢失

RDB 文件是一个经过压缩的二进制文件,还可以通过该文件还原生成 RDB 文件时的数据库状态

10.1 RDB 文件的创建与载入

SAVE、BGSAVE命令生成 RDB 文件

SAVE 命令会阻塞 Redis 服务器进程,直到文件创建完毕,阻塞期间无法处理任何请求

BGSAVE 命令会派生子进程,由子进程负责创建 RDB 文件,服务器父进程继续处理命令请求

创建 RDB 文件的实际工作由 rdb.c/rdbSave 完成,两个命令会以不同的方式调用此函数

RDB 文件的载入工作在服务器启动时自动执行的,只要检测到 RDB 文件存在,自动载入 RDB 文件

AOF文件更新频率通常比 RDB 文件的更新频率高,所以:

如果服务器开启了 AOF 持久化功能,服务器会优先使用 AOF 文件来还原数据库状态 只有在 AOF 持久化功能关闭才会使用 RDB 文件来还原状态

10.1.1 SAVE 命令执行时的服务器状态

阻塞,只有命令执行完成后客户端的命令才会被处理

10.1.2 BGSAVE 命令执行时的服务器状态

服务器可以继续处理命令请求,但有些区别

SAVE 命令被拒绝 BGSAVE 命令也被拒绝 BGREWRITEAOF 不能同时执行 BGSAVE 在执行,被延迟到前者完成后 正在执行,BGSAVE 被拒绝 性能方面考虑,两个子进程同时执行大量写入操作

10.1.3 RDB 文件载入时服务器的状态

阻塞

10.2 自动间隔性保存

设置服务器配置 save 选项,让服务器妹隔一段时间自动执行一次BGSAVE 选项

 save 900 1
save 300 10
save 60 10000
 

在 900 s 内,对数据库进行了至少一次修改

同理

三个条件满足一个,BGSAVE 命令就会执行

10.2.1 设置保存条件

 save 900 1
save 300 10
save 60 10000
 

以上为默认设置,如果没有指定配置参数或者传入启动参数方式

服务器会根据 save 选项设置 redisServer.saveparams 属性

默认情况如下:

10.2.2 dirty 计数器和 lastsave 属性

dirty计数器 记录距离上一次执行 SAVE 命令或者 BGSAVE 命令之后服务器对数据库进行了多少次修改 lastsave UNIX 时间戳 记录了服务器上一次成功执行 SAVE 命令或 BGSAVE 命令的时间

服务器成功执行一次数据库修改命令之后就对 dirty 计数器进行更新

10.2.3 检查保存条件是否满足

serverCron 默认每隔 100 ms 执行一次,对运行的服务器维护,其中一项工作就是检查设置的保存条件是否满足,是则执行 BGSAVE 命令

10.3 RDB 文件结构

完整的 RDB 文件结构如下:

常量:全大写单词

变量和数据:全小写单词

REDIS:5 字节,保存 “REDIS” 5 个字符,方便程序快速分辨为 RDB 文件

RDB 为二进制数据,“REDIS” 保存的不是 c 字符串

db_version:4 字节,为字符串表示的常数, REB 版本号

database

零个或多个数据库,以及数据库中的键值对数据

如果数据库状态为空,此处也为空,长度 0 字节

数据库状态非空,根据情况不同,长度不同

EOF:常量,1 字节,标志 RDB 文件正文内容结束,即所有数据库所有键值对载入完成

check_num:8 字节无符号整数,校验和,通过前四个部分计算而来,载入时计算是否与之相同验证文件是否损坏

10.3.1 database 部分

database 可以保存任意多个非空数据库

假设 0 号、3 号数据库非空, RDB 文件如图,database 代表 0 号数据库中的所有键值对

database 0 又可以再细分

SELECTDB:1 字节,表明接下来读入的是数据库号码

db_number:数据库号码,可以为1 3 5 字节

key_value_pairs:数据库中的所有键值对数据,如果有过期时间也会保存在一起

10.3.2 key_value_pairs 部分

不带过期时间的键值对

TYPE KEY VALUE TYPE:1 字节

value:字符串对象,同上襦的 String 类型

带过期时间的键值对

EXPIRETIME_MS MS TYPE KEY VALUE EXPIRETIME_MS:1 字节,告知程序即将读入的是毫秒为单位的过期时间 ms:8 字节的带符号整数,毫秒为单位为 UNIX 时间戳

10.3.3 value 编码

1.字符串对象:REDIS_RDB_TYPE_STRING

value 保存的为字符串对象,编码有 REDIS_ENCODING_INT 或者 REDIS_ENCODING_RAW

REDIS_ENCODING_INT

长度不超过 32 位的整数

ENCODING 可以是 REDIS_RDB_ENC_INT8、REDIS_RDB_ENC_INT16、REDIS_RDB_ENC_INT32 代表使用几位来保存整数值 integer

REDIS_ENCODING_RAW

字符串对象

压缩与不压缩保存

小于等于 20 字节,原样保存

大于 20 字节,压缩之后再保存

在服务器打开 RDB 文件压缩功能进行的

否则总是无压缩保存

无压缩

压缩

REDIS_RDB_ENC_LZF:常量,表示字符串被 LZF 算法压缩了,程序会对后面三个字段使用解压缩 compressed_len:压缩之后的长度 origin_len:压缩之前的长度 compressed_string:压缩之后的字符串 2.列表对象:REDIS_RDB_TYPE_LIST

value 保存的是 REDIS_ENCODING_LINKEDLIST 编码的列表对象

list_length:列表长度,列表保存了多少个项

item:列表的列表项,每个列表项都是字符串对象

包含长度与实际值

3.集合对象:REDIS_RDB_TYPE_SET

REDIS_ENCODING_HT

set_size:集合大小

elem:字符串对象

包含长度与实际值

4.哈希表对象:REDIS_RDB_TYPE_HASH

REDIS_ENCODING_HT

键与值相邻排列

5.有序集合对象:REDIS_RDB_TYPE_ZSET

REDIS_ENCODING_SKIPLIST

成员与分值紧挨,分值为 double 浮点数,在 double、字符串中互相转换

6.INTSET 编码集合:REDIS_RDB_TYPE_INTSET

整数集合与字符串互相转换

7.ZIPLIST 编码的列表、哈希表或者有序集合

REDIS_RDB_TYPE_LIST_ZIPLIST

REDIS_RDB_TYPE_HASH_ZIPLIST

REDIS_RDB_TYPE_ZSET_ZIPLIST

压缩列表

压缩列表转换字符串

字符串保存到 RDB

字符串转换压缩列表

根据 TYPE 设置类型

REDIS_RDB_TYPE_LIST_ZIPLIST:列表 REDIS_RDB_TYPE_HASH_ZIPLIST:哈希表 REDIS_RDB_TYPE_ZSET_ZIPLIST:有序集合

Redis设计与实现 第 10 章 RDB 持久化

标签:czc   功能   属性   包含   否则   流程   对象   src   不同的   

查看更多关于Redis设计与实现 第 10 章 RDB 持久化的详细内容...

  阅读:25次