当前位置:网站首页>[Study Notes] Persistence of Redis
[Study Notes] Persistence of Redis
2022-08-10 13:21:00 【Tiejia Xiaobao classmate】
【学习笔记】Redis的持久化
前言
持久化简介
持久化(Persistence):即把数据(如内存中的对象)保存到可永久保存的存储设备中(如磁盘).
在Redis中有RBD和AOF两种持久化方式,But generally defaultRDB.

RDB
默认中RedisThe first is to save the in-memory database snapshot under the namedump.rdb的二进制文件中.
save
我们能通过saveto configure the persistence strategy.
save N M #让redis在“N秒内至少有M个改动”才会触发一次rdb持久化操作.
#例如:
save 100 60 #表示在100秒内有60个改动
当执行save命令时,Redis同步做快照操作,在快照执行过程中会阻塞所有来自客户端的请求.当redis内存中的数据较多时,通过该命令将导致Redis较长时间的不响应.所以不建议在生产环境上使用这个命令,而是推荐使用bgsave命令.

bgsave
Redis借助了linux系统的写时复制(Copy-On-Write)技术,在生成快照的同时,仍然可以接收命令处理数据.简单来说,bgsave线程是由主线程fork生成的子线程,可以共享主线程所有的内存数据.bgsave线程运行后,开始读取主线程的内存数据,也就是redis的内存数据,将内存数据写入到dump.rdb文件中.此时,如果主线程处理的命令都是读操作,则bgsave线程不受影响.如果主线程处理了写操作,则会对该命令操作的数据复制一份,生成副本,bgsave线程会把这个副本写入到dump.rdb文件中,而在这个过程中,主线程仍可执行命令.

和save的对比:
| save | bgsave | |
|---|---|---|
| IO类型 | 同步 | 异步 |
| 是否阻塞其他命令 | 是 | 否 |
| 复杂度 | O(n) | O(n) |
| 优点 | Does not consume additional memory | 不阻塞操作 |
| 缺点 | 阻塞操作 | consumes additional memory |
RDB的优点:
- 因为
dump.rdb是二进制文件,When disaster-level data loss occurs,Using binary files can be easily restored. - 生成RDB文件的时候,redis主进程会fork()一个子进程来处理所有保存工作,主进程不需要进行任何磁盘IO操作.
- RDB 在恢复大数据集时的速度比AOF的恢复速度要快.
RDB的缺点:
- RDB方式数据没办法做到实时持久化/秒级持久化.因为bgsave每次运行都要执行fork操作创建子进程,频繁执行成本过高.
- 在一定间隔时间做一次备份,所以如果redis意外down掉的话,Modified data after the last snapshot will be lost(数据有丢失).
AOF(Append-Only File)
Redis 默认不开启.AOF采用日志的形式来记录每个写操作,并追加到文件中.开启后,执行更改Redis数据的命令时,就会把命令写入到AOF文件中.
Redis 重启时会根据日志文件的内容把写指令从前到后执行一次以完成数据的恢复工作.
手动配置:
# appendonly yes
AOF可以配置三种刷盘策略:
appendfsync always:每次执行写命令都会刷盘,非常慢,也非常安全.
appendfsync everysec:每秒刷盘一次,兼顾性能和安全.
appendfsync no:将刷盘操作交给系统,很快,不安全.
AOF重写
随着时间的推移,AOFThe backup file will get bigger and bigger!This not only results in taking up a lot of disk space,will also make some移动复制,加载分析Seems very time consuming!
To reduce file growth,可以采用 压缩 way to reduce the memory of a file.
如下两个配置可以控制aop文件重写的频率:
# auto‐aof‐rewrite‐min‐size 64mb: -- aof文件至少达到了64m才会触发重写
# auto‐aof‐rewrite‐percentage 100: -- 距离上次重写增长了100%才会再次触发重写
AOF也可以手动触发重写:bgrewriteof
注意,AOF重写redis会fork出一个子进程去做(与bgsave命令类似),不会对redis正常命令处理有太多影响
重写的流程:
- 主进程会
fork一个子进程出来进行AOF重写,It is not a rearrangement of the original file,而是直接读取redisExisting key-value pairs in service memory,Then replace each key-value pair with a single command,写入到新的AOF文件中 - 在
fork子进程这个过程中,服务端仍然可以对外提供服务,In this period of time when the child process is rewritten,,主进程的数据更新操作,会缓存到aof_rewrite_buf中,也就是单独开辟一块缓存来存储重写期间收到的命令,当子进程重写完以后再把缓存中的数据追加到新的aof文件. - 当所有的数据全部追加到新的
aof文件中后,会把旧的aof文件替换成新的aof文件,此后所有的操作都会被写入新的aof文件. - 如果在
rewrite过程中出现故障,不会影响原来aof文件的正常工作,只有当rewrite完成后才会切换文件.因此这个rewrite过程是比较可靠的.

在aof_bufcache to oldaofThere is actually a child process in the middle of the file,将aof_bufThe data in the cache is synchronized toaof文件中取.
AOF相关问题
问题1:数据都是实时持久化到磁盘吗?
虽然每次执行更改Redis数据库内容的操作时,AOF都会将命令记录在AOF文件中,但是事实上,由于操作系统的缓存机制,数据并没有真正地写入硬盘,而是进入了aof_buf缓存中.在默认情况下系统每30秒会执行一次同步操作.以便将aof_bufThe contents of the cache are actually written to disk.
在这30If the system exits abnormally in the process of seconds, it will be causedaof_bufData in cache is lost.这个时候就需要Redis在写入AOFAfter the file is actively requested the system willaof_bufCache contents are synced to disk.在redis.conf中通过如下配置来设置同步机制.
fork()出一个子进程,Via subprocess willaof_bufThe data in the cache is synchronized to disk:
问题2:为什么要AOF重写?
比如我有业务很简单,就来回delete set同一个key.就这个业务运行了10年,那么aof文件将记录无数个delete k1, set k1.其实都是重复的,但是我aof每次都追加,文件变成了1T大小.这时候Redis宕机了,要恢复,你想想1TB大小的aof文件去恢复,累死了.最主要的是1TB大小只记录了两个命令,所以压缩其实就是来处理这件事的.
RDB于AOF对比
| 命令 | RDB | AOF |
|---|---|---|
| 启动优先级 | 低 | 高 |
| 体积 | 小 | 大 |
| 恢复速度 | 快 | 慢 |
| 数据安全性 | 容易丢失数据 | 根据策略决定 |
混合持久化
如果我们采用 RDB 持久化会丢失一段时间数据.如果我们采用 AOF 持久化,AOF日志较大,重放比较慢.
Redis 4.0 为了解决这个问题,支持混合持久化.将 RDB 文件的内容和增量的 AOF 日志文件存在一起.
混合持久化同样也是通过 bgrewriteaof 完成的,不同的是当开启混合持久化时,fork出的子进程先将共享的内存副本全量的以 RDB 方式写入 AOF 文件,然后在将重写缓冲区的增量命令以 AOF 方式写入到文件,写入完成后通知主进程更新统计信息,并将新的含有RDB格式和 AOF 格式的 AOF 文件替换旧的的 AOF 文件.简单的说:新的AOF文件前半段是RDB格式的全量数据后半段是AOF格式的增量数据.
于是在 Redis 重启的时候,可以先加载 rdb 的内容,然后再重放增量 AOF 日志就可以完全替代之前的 AOF 全量文件重放,重启效率因此大幅得到提升.
参考文章链接:
| 文章1 |
|---|
| 文章2 |
| 文章3 |
边栏推荐
- Redis 定长队列的探索和实践
- Keithley DMM7510 accurate measurement of ultra-low power consumption equipment all kinds of operation mode power consumption
- 47Haproxy Cluster
- 22!Beijing Changping District notified catering service enterprises with food safety problems
- 需要被记录的OpenStack相关的命令_自己用
- sprintboot项目通过interceptor和filter实现接入授权控制
- 2022-08-09:以下go语言代码输出什么?A:否,会 panic;B:是,能正确运行;C:不清楚,看投票结果。 package main import ( “fmt“ “syn
- 九宫格抽奖动效
- BEVDet4D: Exploit Temporal Cues in Multi-camera 3D Object Detection 论文笔记
- C# InitializeComponent() does not exist in the current context
猜你喜欢

3DS MAX 批量导出文件脚本 MAXScript 带界面

3DS MAX batch export file script MAXScript with interface

DNS欺骗-教程详解

【目标检测】小脚本:提取训练集图片与标签并更新索引

Basic knowledge of switches

一个 CRM One Order Application log 的单元测试报表

Nanodlp v2.2/v3.0光固化电路板,机械开关/光电开关/接近开关的接法和系统状态电平设置

Proprietary cloud ABC Stack, the real strength!

想通这点,治好 AI 打工人的精神内耗

Digicert EV证书签名后出现“证书对于请求用法无效”的解决方案
随机推荐
NodeJs原理 - Stream(二)
bgp双平面实验 路由策略控制流量
娄底妆品实验室建设规划构思
Redis上云迁移实践
海外邮件发送指南(二)
Codeforces Round #276 (Div. 1) D. Kindergarten
递归递推之计算组合数
bgp dual plane experiment routing strategy to control traffic
Efficient and Robust 2D-to-BEV Representation Learning via Geometry-guided Kernel Transformer Paper Notes
一个 CRM One Order Application log 的单元测试报表
C# 当前上下文中不存在InitializeComponent()
C# error The 'xmins' attribute is not supported in this context
讯飞创意组别 全国选拔赛成绩公布说明
娄底疾控中心实验室设计理念说明
山水的高度
22家!北京昌平区通报存在食品安全问题餐饮服务企业
Loudi Sewage Treatment Plant Laboratory Construction Management
ArcMAP has a problem of -15 and cannot be accessed [Provide your license server administrator with the following information:Err-15]
47Haproxy Cluster
Guidelines for Sending Overseas Mail (2)
