什么是 AOF 重写?AOF 重写机制的流程是什么?

引言:在Redis中,持久化是确保数据持久性和可恢复性的重要机制之一。除了常见的RDB(Redis Database)持久化方式外,AOF(Append Only File)也是一种常用的持久化方式。AOF持久化通过记录Redis服务器执行的写命令来实现数据的持久化。本文将探讨AOF重写机制的原理、实现方式以及其在Redis持久化中的作用,以帮助读者更好地理解和利用Redis中的AOF持久化机制。

题目

什么是 AOF 重写?AOF 重写机制的流程是什么?

推荐解析

什么是 AOF 重写?

AOF (Append Only File)是 Redis 持久化的一种方式,其通过记录 Redis 执行的每一条命令,重启之后通过重新执行 Redis 中的命令来恢复数据。

不过,随着 Redis 执行命令的不断增多,AOF 文件越来越大,但是很多数据其是不一定都是有意义的,比如原来 set age 10,后面又来个 set age 18,然后又来个 set age 30,我们这个时候就会发现,只有最后一个 age 是有意义的,前面都是没有用的。

AOF 重写就是指通过当前状态,重新生成最新的 AOF 操作命令记录的过程。

AOF 的重写流程?

AOF 文件的重写流程主要就一句话,“一次拷贝,两处日志”。

  • 一次拷贝:重写发生的时候,主进程会 fork 出一个子进程,然后子进程与主进程共享 Redis 物理内存,让子进程将这些 Redis 数据写入重写日志。
  • 两处日志:重写发生的时候,我们需要注意 AOF 缓冲和 AOF 重写缓冲;当数据进行重写的时候,如果此时有新的写入命令执行,会由主进程分别写入 AOF 缓冲和 AOF 重写缓冲;AOF 缓冲用于保证此时即使发生宕机了,原来的 AOF 日志也是完整的,可以用于恢复。AOF 重写缓冲用于保证新的 AOF 文件也不会丢失最新的写入操作。

AOF 的重写流程大致就是这样了,相信到这里大家只要熟读八股文,那肯定是没有任何问题的,接下里面试官肯定会问那有什么办法可以优化呢?一般人都会回答 RDB + AOF 的混合持久化,90 % 的人都会这样回答,但是这样的回答面试官听太多了,那有什么办法可以优化一下呢?必须有的,接下来就是我们今天文章的主角 Multi Part AOF

原有 AOF 重写的弊端

我们先来分析一下原先的方案,其流程图主要如下所示:

这个弊端主要有 3 个方面的内容,在这里我总结一下:

​ 1)内存开销: 在进行 AOF 重写的时候,AOF 缓冲与 AOF 重写缓冲区中的内容是一致的,这样就代表一样的内容得写两遍,带来了不必要的内存开销;

​ 2)磁盘开销:在重写的时候,AOF 缓冲区需要刷盘旧的日志文件到新的 AOF 日志,而 AOF 重写缓冲区的内容需要绕过一段很长的链路写入到新的 AOF 日志,两份的数据明明是一样的,但是却需要磁盘两次写入,这也带来了不必要的磁盘开销;

​ 3)CPU 开销: 在进行 AOF 重写的时候,主进程需要将新写入的数据写入到 AOF 重写缓冲区当中,主进程还需要通过管道将 AOF 重写缓冲区的的数据发送给子进程,然后子进程还需要将这些数据写入到新的日志文件。由于 Redis 的读写操作单线程的,这些操作都是串行执行的,所以会带来不必要的 CPU 开销。

在这个过程中,我们会发现两个核心点:

​ 1)AOF 重写缓冲区和 AOF 缓冲区内的数据是一样的;

​ 2)父子进程之间传输数据这个操作耗时太久了;

以下是 Redis 的官方文档,我们会发现 7.0 之前就是我们所说的点,既然官方都说这个是 Redis 7.0 之前了,那 Redis 7.0 之后发生了什么呢,接下来让我们来探究一下今天的主角 MP-AOF

Multi Part AOF

千呼万唤始出来,Multi Part AOF 出来了,以下是官方文档对他的一端描述

Since Redis 7.0.0, when an AOF rewrite is scheduled, the Redis parent process opens a new incremental AOF file to continue writing. The child process executes the rewrite logic and generates a new base AOF. Redis will use a temporary manifest file to track the newly generated base file and incremental file. When they are ready, Redis will perform an atomic replacement operation to make this temporary manifest file take effect. In order to avoid the problem of creating many incremental files in case of repeated failures and retries of an AOF rewrite, Redis introduces an AOF rewrite limiting mechanism to ensure that failed AOF rewrites are retried at a slower and slower rate.

官方文档地址:https://redis.io/topics/persistence

你会发现他说的全是英文,其实核心已经藏在他的名字里了 Multi Part AOF, 即将原来一个 AOF 文件拆分成多个 AOF 文件,在 Multi Part AOF 中,文件被分成 3 种类型,分别如下:

  • Base: 表示基于 AOF 文件,记录了基本的命令,一般由子进程通过重写产生,只有一个。
  • Incr:表示增量 AOF 文件,记录了重写过程中新增的操作指令,一般会在 AOF 重写开始执行时被创建,该文件可能存在多个。
  • History:表示历史 AOF 文件,他主要由 Base 和 Infr 变化而来,每次 AOF 重写完成后,本次 AOF 重写之前对应的 Base 和 Incr 的 AOF 文件都会变成 Histroy,History 类型的 AOF 会被 Redis 自动删除。

然后为了管理 AOF 文件,我们引入了一个 mainfest(清单)文件来跟踪和管理这些 AOF。于此同时,为了方便 AOF 备份和拷贝,我们将所有的 AOF 文件和 mainfest 文件放到一个单独的目录文件目中,目录文件名由 appenddirname配置(Redis 7.0新增配置项)决定。

下图是 Multi Part AOF 的流程:

从图中我们可以看到,现在重写阶段,只需要在主进程中将新请求数据写到 AOF 缓存中就可以了,然后 AOF 缓冲区的文件最后形成 Incr AOF 日志的内容,然后在子进程中,根据数据库 fork 的数据,生成一个 Base AOF 文件,两者合一构成 Redis 的全部数据。

然后在 AOF 重写结束后,主进程会更新 mainifest 文件的内容,将新生成的 Base AOF 文件和 Incr AOF 文件的内容加入,并且将之前的 Base AOF 文件和 Incr AOF 文件标记为 Histroy,然后等待 Redis 异步删除。

到此为止,我们会发现一件事,现在的 AOF 重写有了很大的改进:

  1. 在 AOF 重写期间不需要 AOF 重写缓冲区了
  2. 然后也不需要父子进程通过管道进行数据传输

从一定程度上减缓了 CPU、内存、磁盘的性能损耗,也降低了 Redis 的代码复杂度。

总结

原有的 AOF 重写由于引入了 AOF 重写缓冲区以及父子进程通信,导致了 Redis CPU、磁盘、内存的性能损耗,Redis 7.0 引入了 MP-AOF 的方案进行优化,到这里为止,各位以后说 AOF 持久化优化的时候又多了一个装逼的点,直接和面试官说我看过 Redis 的官方文档,这样不就加大分了嘛,好了,到这里就结束了,小伙伴们赶紧学起来吧。

其他补充

鱼聪明 AI 的回答:

鱼聪明 AI 地址:https://www.yucongming.com/

Redis 提供了两种主要的持久化机制,分别是 RDB(Redis DataBase)和 AOF(Append Only File)。这两种机制可以确保 Redis 服务器在重启时能够恢复数据,但它们的工作原理和恢复流程略有不同。

RDB 持久化

RDB 是 Redis 的一种快照持久化方式,它可以将 Redis 内存中的数据保存到硬盘上的一个文件中。RDB 的恢复流程如下:

  1. 生成 RDB 文件
    • Redis 服务器根据设定的策略(如定期快照或手动触发)生成 RDB 文件。
    • 在生成 RDB 文件期间,Redis 会阻塞所有客户端请求,以确保数据的一致性和完整性。
  2. 保存 RDB 文件
    • 一旦生成完毕,RDB 文件会被保存到硬盘上指定的位置。这个位置可以在 Redis 配置文件中进行配置。
  3. 恢复过程
    • 当 Redis 服务器重启时,它会尝试加载最近保存的 RDB 文件。
    • 如果 RDB 文件存在且没有损坏,Redis 会从中读取数据并加载到内存中,完成恢复过程。
    • 一旦加载完成,Redis 就可以继续接受客户端请求。

AOF 持久化

AOF 是一种基于日志的持久化方式,它通过记录 Redis 服务器接收到的每个写操作来实现数据持久化。AOF 的恢复流程如下:

  1. AOF 文件
    • Redis 将每个写操作追加到 AOF 文件的末尾。AOF 文件包含一个完整的操作日志,描述了服务器执行的所有写操作。
  2. 重放 AOF 文件
    • 当 Redis 服务器重启时,它会尝试通过重放 AOF 文件中的写操作来重建数据集的状态。
    • Redis 服务器会按照 AOF 文件中写操作的顺序,逐条执行这些操作,将数据集恢复到重启前的状态。
  3. AOF 文件的持久化
    • Redis 提供了不同的 AOF 持久化策略,可以通过配置文件设置:
      • appendfsync always:每次写操作都会同步到 AOF 文件,这是最安全的方式,但也最慢。
      • appendfsync everysec:每秒同步一次,提供了很好的性能和持久性的折中。
      • appendfsync no:完全依赖于操作系统的 fsync。这种方式速度最快,但数据可能会有一定的丢失风险。

恢复机制对比

  • RDB 恢复:由于 RDB 是一个快照文件,恢复速度相对较快,但是可能会丢失最后一次快照后的修改。
  • AOF 恢复:AOF 通过重放操作日志来恢复数据,因此通常情况下能够保证数据更为完整,但可能会因为重放时间较长而导致恢复速度较慢。

选择 RDB 还是 AOF 作为持久化方式,通常取决于对数据完整性、恢复速度以及系统性能的不同要求。在生产环境中,通常会根据实际需求和配置选择合适的持久化方式或者两者结合使用。

欢迎交流

本文主要介绍什么是 AOF 重写,以及 AOF 重写的流程和原有低版本下 Redis 重写的弊端,以及高版本后升级的 Multi Part AOF,在文末还有三个问题,欢迎小伙伴在评论区留言,近期面试鸭小程序已全面上线,想要刷题的小伙伴可以积极参与!

1)AOF 重写的触发条件是什么?

2)AOF 重写如何实现压缩和优化?

3)AOF 重写的影响和性能考量是什么?

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/25321.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

基于Gabor小波特征提取和PSO-SVM的胃溃疡分类(MATLAB R2018a)

Gabor滤波器是在测不准原则下能够在时域和频域中唯一能取得最佳的联合分辨率函数(测不准原则:是指在时域与频域中都要获得任何的测量精度那是不可能同时实现的,要使时域分辨率有所提高,必须牺牲频域的分辨率,反之亦然&…

Java | Leetcode Java题解之第134题加油站

题目&#xff1a; 题解&#xff1a; class Solution {public int canCompleteCircuit(int[] gas, int[] cost) {int n gas.length;int i 0;while (i < n) {int sumOfGas 0, sumOfCost 0;int cnt 0;while (cnt < n) {int j (i cnt) % n;sumOfGas gas[j];sumOfCos…

Polar Web【中等】search

Polar Web【中等】search Contents Polar Web【中等】search思路&探索首页一般注入方式 EXP&效果Payload 总结 思路&探索 见到题目标题&#xff0c;预测可能有目录扫描或者输入框查询数据之类情况&#xff0c;具体细节在破解过程中才能清楚 打开站点&#xff0c;显…

如何下载BarTender软件及详细安装步骤

BarTender是美国海鸥科技推出的一款优秀的条码打印软件&#xff0c;应用于 WINDOWS95 、 98 、 NT 、 XP 、 2000 、 2003 和 3.1 版本&#xff0c; 产品支持广泛的条形码码制和条形码打印机&#xff0c; 不但支持条形码打印机而且支持激光打印机&#xff0c;还为世界知名品牌条…

前端-a-date-picker如何设置禁选时间段

想要做到如图所示的效果&#xff0c;代码如下&#xff1a; 第一个是只能选择某一天&#xff0c;第二个是只能选择某一个时间段 <a-date-pickerv-model:value"record.onTimeStr":show-time"{ format: HH:mm }"valueFormat"YYYY-MM-DD HH:mm:ss&qu…

【RAG入门教程02】Langchian的Embedding介绍与使用

Embedding介绍 词向量是 NLP 中的一种表示形式&#xff0c;其中词汇表中的单词或短语被映射到实数向量。它们用于捕获高维空间中单词之间的语义和句法相似性。 在词嵌入的背景下&#xff0c;我们可以将单词表示为高维空间中的向量&#xff0c;其中每个维度对应一个特定的特征…

mm-qcamera-daemon主函数分析

目录 main函数核心 main函数核心 main函数的主要任务包含在一个do{ } while(1)循环中. while循环中主要是监听文件描述符,故mai函数是由文件的读写来进行驱动的。 所有的文件描述符被封装成结构体 read_fd_info_t.其定义如下&#xff1a; /** read_fd_info_t* type -- either …

拯救者Legion Y9000X IRX9 2024(83FD)原装出厂Windows11系统镜像下载

lenovo联想2024款拯救者Y9000X IRX9 笔记本电脑【83FD】OEM预装Win11系统安装包&#xff0c;恢复开箱状态&#xff0c;自带恢复重置还原功能 链接&#xff1a;https://pan.baidu.com/s/1i_sVcnXF4qgsuj02rebe-Q?pwdyefp 提取码&#xff1a;yefp 联想原装WIN11系统自带所有…

Vue2学习(04)

目录 一、组件的三大组成部分 二、组件的样式冲突scoped 三、scoped原理 ​编辑 四、data是一个函数 五、组件通信 1.概念&#xff1a;是指组件与组件之间的数据传递&#xff0c;组件的数据是独立的&#xff0c;无法直接访问其他组件的数据&#xff0c;想用其他组件的数…

Pycharm中import torch报错解决方案(Python+Pycharm+Pytorch cpu版)

pycharm环境搭建完毕后&#xff0c;编写一个py文件demo&#xff0c;import torch报错&#xff0c;提示没有。设置python解释器&#xff1a; 选择conda环境&#xff0c;使用现有环境&#xff0c;conda执行文件找到Anaconda安装路径下Scripts文件夹内的conda.exe&#xff0c;最后…

【Java SE】字符串常量池详解,什么情况下字符串String对象存在常量池,通过==进行判断,字符串创建及截取后是否同一个对象

复习字符串创建方式 字符串的31种构造方法 public String();创建一个空白字符串&#xff0c; 不含有任何内容public String(char[] array);根据字符数组的内容&#xff0c;来创建对应的字符串public String(byte[] array);根据字节数组的内筒&#xff0c;来创建对应的字符串 …

Docker:在DockerHub上创建私有仓库

文章目录 Busybox创建仓库推送镜像到仓库 本篇开始要学习在DockerHub上搭建一个自己的私有仓库 Busybox Busybox是一个集成了三百多个最常用Linux命令和工具的软件&#xff0c;BusyBox包含了很多工具&#xff0c;这里拉取该镜像推送到仓库中&#xff1a; 安装 apt install …

leetcode(力扣)第15题-三数之和---使用c语言双指针法,二级指针的应用

题目&#xff1a; 15. 三数之和 - 力扣&#xff08;LeetCode&#xff09; 编写过程的问题&#xff1a; 记住线索 1、对数组使用快排排序&#xff1b;2、固定 a 对 b、c 使用双指针&#xff1b;3、注意去重问题。函数返回值的类型。{1&#xff0c;2&#xff0c;-3}。结果作为…

如何获取当前dll或exe模块所在路径?

有时我们需要在当前运行的dll或exe模块中去动态加载当前模块同路径中的另一个库&#xff0c;或者启动当前模块同路径中的另一个exe程序&#xff0c;一般需要获取当前模块的路径&#xff0c;然后去构造同路径下目标模块的绝对路径&#xff0c;然后通过该绝对路径去加载或启动该目…

高速USB转串口芯片CH343

CH343封装 截止目前&#xff0c;主要封装有 SOP16: CH343G QFN16: CH343P ESSOP10: CH343K,截止24年6月未生产 CH343串口速度 最高串口速度&#xff1a; 6Mbps,比CH340的2M&#xff0c;快3倍 1、概述 参考版本&#xff1a;1E CH343 是一个 USB 总线的转接芯片&#xff0c;…

Java Web学习笔记31——Maven介绍

Maven&#xff1a;Java项目的构建工具。 Maven&#xff1a; Maven是Apache旗下的一个开源项目&#xff0c;是一款用于管理和构建Java项目的工具。 Apache软件基金会&#xff0c;成立于1999年7月&#xff0c;是目前世界上最大的最受欢迎的开源软件基金会&#xff0c;也是一个专…

Java | Leetcode Java题解之第132题分割回文串II

题目&#xff1a; 题解&#xff1a; class Solution {public int minCut(String s) {int n s.length();boolean[][] g new boolean[n][n];for (int i 0; i < n; i) {Arrays.fill(g[i], true);}for (int i n - 1; i > 0; --i) {for (int j i 1; j < n; j) {g[i]…

深度学习中几种常见数据标准化方法

目录 一、介绍 二、总结 三、详情 1. StandardScaler 2. MinMaxScaler 3. RobustScaler 4. MaxAbsScaler 5. Normalizer 6. QuantileTransformer 7. PowerTransformer 8. Log Transform 四、示例 五、心得 一、介绍 方法名称缩放范围适用条件StandardScaler均值…

python 判断点和线段相交

python 判断点和线段相交 import numpy as np import cv2 import numpy as npdef point_to_line_distance(points, line_segments):# line_segments [[549, 303], [580, 303]]# points [565, 304]x0, y0, x1, y1line_segments[0][0], line_segments[0][1], line_segments[1]…

【python】OpenCV GUI——Trackbar(14.2)

学习来自 OpenCV基础&#xff08;12&#xff09;OpenCV GUI中的鼠标和滑动条 文章目录 GUI 滑条介绍cv2.createTrackbar 介绍牛刀小试 GUI 滑条介绍 GUI滑动条是一种直观且快速的调节控件&#xff0c;主要用于改变一个数值或相对值。以下是关于GUI滑动条的详细介绍&#xff1a…