Redis 持久化

目录

[​编辑一、单节点 Redis 的问题](#编辑一、单节点 Redis 的问题)

[二、Redis 持久化](#二、Redis 持久化)

[1、RDB 持久化](#1、RDB 持久化)

[2、RDB 原理](#2、RDB 原理)

[3、RDB 总结](#3、RDB 总结)

[4、AOF 持久化](#4、AOF 持久化)

[5、AOF 配置](#5、AOF 配置)

[6、AOF 文件重写](#6、AOF 文件重写)

[7、RDB 和 AOF 的对比](#7、RDB 和 AOF 的对比)


一、单节点 Redis 的问题

数据丢失问题:Redis 是内存储存,服务重启可能会丢失数据

并发能力问题:Redis 的并发能力虽然不错,但是无法满足部分高并发的场景 (如 618)

故障恢复问题:如果 Redis 宕机,则服务就不可用了,所以我们得保证整个 Redis 集群是持续可用的

存储能力问题:Redis 基于内存,单节点能存储的数据量有限


二、Redis 持久化

1、RDB 持久化

RDB全称Redis Database Backup file(Redis数据备份文件),也被叫做Redis数据快照

简单来说就是把内存中的所有数据都记录到磁盘中。当Redis实例故障重启后,从磁盘读取快照文件,恢复数据。

快照文件称为RDB文件,默认是保存在当前运行目录。

RDB 是把内存中的数据都记录到磁盘中,而磁盘的 IO 是比较大的,一旦整个数据量比较大,耗时就会比较久,那么等待执行完成,才会返回 ok ,主进程才会去执行其它的请求

因此并不推荐使用 RDB ,这个方式比较适合用于整个进程即将停止的时候使用 save ,而更加推荐使用 bgsave

这个保存的命令是在后台异步执行,因为它是由一个额外的进程(子进程)来执行 RDB 的,主进程不会受到影响

所以这个方式比较适合于在 Redis 运行的过程中使用

Redis 内部有触发 RDB 的机制,可以在 redis.conf 文件中找到:

同样的,RDB 的其它配置也可以在 redis.conf 文件中设置


2、RDB 原理

我们知道:当满足一定的条件时,就会触发 bgsave ,完成异步的持久化,异步持久化就是开启一个子进程,由这个子进程去完成对内存数据的读取和写入 RDB

因为是异步的,所以可以做到对主进程几乎零阻塞

为什么说是几乎零阻塞呢?

因为子进程是通过 fork 主进程得到的,这个 fork 的过程是阻塞的,此时主进程只能干这一件事

物理内存可以理解成计算机里面的内存条

主进程要实现对内存中数据的读写,肯定是要在内存中进行操作的,但是在 Linx 系统中,所有的进程都没有办法直接操作物理内存,而是由操作系统给每个内存分配一个虚拟内存

那么主进程只能操作虚拟内存,而后操作系统会维护一个虚拟内存与物理内存之间的映射关系表(页表),从而实现对物理内存数据的读写

而我们执行 fork 的时候,会去创建一个子进程

**fork 也就是把页表(映射关系)给拷贝给子进程,当子进程有了和主进程相同的映射关系之后,当子进程在操作自己的虚拟内存时,因为映射关系与主进程一样,所以最终一定可以映射到相同的物理内存区域,**这样也就实现了子进程与主进程之间内存空间的共享

此时就无需拷贝内存数据,直接实现了内存共享,这个速度就会变得非常的快,阻塞的时间也就尽可能的缩短了

而后再将数据写到磁盘当中形成新的 RDB 文件,替换掉旧的 RDB 文件

那么子进程在写 RDB 的过程当中,主进程可不可以接受用户的请求,来去修改内存中的数据呢?

可以的,但是如果这个时候,主进程在修改数据,而子进程同时在读数据,读与写之间就会存在冲突

为了避免这个问题的发生,fork 底层会采用 copy-on-write 技术:

当主进程执行读操作的时候,访问共享技术

当主进程执行写操作的时候,则会拷贝一份数据,进行写操作

为了预防一些极端情况的发生,Redis 一般情况下都会预留一些空间,来防止内存溢出的情况发生


3、RDB 总结

RDB 方式 bgsave 的基本流程?

fork 主进程得到一个子进程,共享内存空间

子进程读取内存数据并写入新的 RDB 文件

用新的 RDB 文件替换掉旧的 RDB 文件

RDB 会在什么时候执行? save 60 1000 代表什么含义?

save:默认是服务停止时执行

bgsave:要看停止的条件

代表 60 秒内至少执行你提供 1000 次修改则触发 RDB

RDB 的缺点:

RDB执行间隔时间长,两次RDB之间写入数据有丢失的风险

fork子进程、压缩、写出RDB文件都比较耗时


4、AOF 持久化

AOF全称为Append Only File**(追加文件)**。Redis处理的每一个写命令都会记录在AOF文件,可以看做是命令日志文件。

比如: 我现在执行一个 set num 123 时,会先把 set num 123 记录到 redis 的 key-value 结构里,而后还会把命令写到 AOF 的文件当中

如果将来 redis 出现了故障,我要恢复,那么就可以直接读取 AOF 文件,把里面的命令从头开始执行一遍,此时里面的数据就可以恢复到原始状态了


5、AOF 配置

AOF 默认是关闭的,需要修改 redis.conf 配置文件来开启 AOF

AOF 的命令记录的频率也可以通过 redis.conf 文件来配置

上述三种命令记录策略的对比:

6、AOF 文件重写

AOF 因为是记录命令,AOF文件会比RDB文件大的多

而且AOF会记录对同一个key的多次写操作,但只有最后一次写操作才有意义。

通过执行bgrewriteaof命令,可以让AOF文件执行重写功能,用最少的命令达到相同效果。

Redis 也会在触发阈值时自动去重写 AOF 文件,阈值也可以在 redis.conf 中配置


7、RDB 和 AOF 的对比

RDB和AOF各有自己的优缺点,如果对数据安全性要求较高,在实际开发中往往会结合两者来使用。

相关推荐
了一li2 小时前
Qt中的QProcess与Boost.Interprocess:实现多进程编程
服务器·数据库·qt
码农君莫笑2 小时前
信管通低代码信息管理系统应用平台
linux·数据库·windows·低代码·c#·.net·visual studio
别致的影分身2 小时前
使用C语言连接MySQL
数据库·mysql
京东零售技术4 小时前
“慢”增长时代的企业数据体系建设:超越数据中台
数据库
sdaxue.com4 小时前
帝国CMS:如何去掉帝国CMS登录界面的认证码登录
数据库·github·网站·帝国cms·认证码
o(╥﹏╥)5 小时前
linux(ubuntu )卡死怎么强制重启
linux·数据库·ubuntu·系统安全
阿里嘎多学长5 小时前
docker怎么部署高斯数据库
运维·数据库·docker·容器
Yuan_o_5 小时前
Linux 基本使用和程序部署
java·linux·运维·服务器·数据库·后端
Sunyanhui15 小时前
牛客网 SQL36查找后排序
数据库·sql·mysql
老王笔记6 小时前
MHA binlog server
数据库·mysql