【Redis】Redis中的 AOF(Append Only File)持久化机制

目录

1、AOF日志

2、AOF 的执行顺序与潜在风险

3、如何优化 AOF?(写入策略)

4、AOF重写机制(防止日志文件无限增长)

1、AOF日志

        想象一下,Redis 每次执行写操作的时候,都把这些操作以追加的方式写入一个文件中,然后当你重启 Redis 时,Redis 会从这个文件里读取命令并重新执行,这样就相当于恢复了缓存的数据。这就是 Redis 的 AOF 持久化功能——它专门用来记录写操作(读操作是不会记录的,因为读操作没必要重放)。

        默认情况下,AOF 是关闭的(Redis 6.0 之后已经默认是开启了)。如果你想用它,需要去修改 Redis 的配置文件 redis.conf,把相应的参数打开。只有同步到磁盘中才算持久化保存了,否则依然存在数据丢失的风险,比如说:系统内核缓存区的数据还未同步,磁盘机器就宕机了,那这部分数据就算丢失了。

# 是否开启 AOF 持久化 (默认值: no)
# 改为 yes 表示开启 AOF 持久化功能
appendonly yes

# AOF 持久化文件的名称 (默认值: appendonly.aof)
# 可以自定义 AOF 文件的名称
appendfilename "appendonly.aof"

        AOF 日志就是一个普通的文本文件,里面记录的都是命令,比如执行 set name xiaotao,日志里的内容大概是这样的:

*3
$3
set
$4
name
$7
xiaotao

        这些奇怪的符号看上去可能有点复杂,其实很好理解。*3 表示这个命令由三部分组成,每部分的内容前都有一个 $ 和一个数字,比如 $3 后面是 set,意思是这个部分的内容有 3 个字节(也就是 set 这个命令有 3 个字符)。

2、AOF 的执行顺序与潜在风险

执行顺序:Redis 先执行写操作,再把命令记录到 AOF 日志里,这样做有两个好处:

  1. 避免额外的检查开销:如果先写日志再执行命令,可能会把错误的命令写进日志,那在数据恢复时就会出错。先执行命令再记录日志,确保写进日志的命令都是正确的。
  2. 减少写操作的阻塞:因为日志是在命令成功执行后才写入的,所以不会影响当前的写操作。

潜在风险:虽然 AOF 很强大,但也有一些风险:

  1. 数据丢失风险:因为写命令和写日志是两个步骤,如果 Redis 还没来得及把命令写入日志就宕机了,这部分数据就会丢失。
  2. 阻塞风险:写日志的操作是在主进程完成的,如果硬盘压力大,写日志的速度变慢,就可能阻塞后续的命令执行。

3、如何优化 AOF?(写入策略)

        在 Redis 中,AOF 是通过一种「先缓存、后写盘」的方式来保存数据。写操作完成后,命令会被追加到 server.aof_buf 缓冲区中,然后通过 write() 系统调用将缓冲区数据写入 AOF 文件。不过,数据并没有直接写到硬盘,而是暂时放在操作系统的内核缓冲区(page cache)中,之后由操作系统决定什么时候把这些数据写入硬盘。

        AOF潜在风险的本质都跟 AOF 日志什么时候写入硬盘有关。所以 Redis 提供了几种不同的写入策略,由 redis.conf 配置文件中的 appendfsync 配置项控制,你可以根据需求来调整。这三种策略是:

(一)always(总是)

  • 含义:每次写操作命令执行完后,立即将 AOF 日志数据写入硬盘。
  • 优点:数据几乎不会丢失,因为每次操作都会马上保存到硬盘。
  • 缺点:性能最差,因为频繁的硬盘操作会拖慢 Redis 的主进程。

(二)everysec(每秒)

  • 含义:写操作执行后,命令会先被写入到 AOF 文件,但每隔一秒才同步到硬盘。
  • 优点:在性能和数据安全之间做了折中,减少了频繁写盘带来的性能损耗,同时每秒进行一次写盘,丢失数据的风险也相对较小。
  • 缺点:如果 Redis 在这 1 秒内宕机,最后的写操作数据可能会丢失。

(三)no(不控制)

  • 含义:不由 Redis 控制写盘时机,而是交给操作系统处理,数据写入内核缓冲区后,操作系统会自行决定什么时候写入硬盘。
  • 优点:性能最好,因为 Redis 不会干涉写盘,减少了 Redis 主进程的负担。
  • 缺点:数据丢失的可能性更大,因为操作系统决定写入的时机不可预知,如果宕机,可能会丢失大量数据。

三种策略的优缺点对比

策略数据安全性性能表现适用场景
always数据最安全,几乎不丢失性能最差适合要求高可靠性的数据存储场景
everysec数据丢失量最多 1 秒性能较好,折中方案大多数场景适用,平衡性能和数据丢失风险
no可能丢失较多数据性能最好适合高性能要求,不介意数据丢失的场景

所以要根据场景来选择写入策略

  • 如果你的系统对性能要求高,可以选择 no 策略,最大化提升 Redis 的执行效率。
  • 如果你不能容忍任何数据丢失,那就选择 always 策略,确保每次操作都立即写入硬盘。
  • 对大多数业务场景来说,everysec 是一个比较好的折中选择:它既能保持不错的性能,又能在保证数据安全方面做得比较好,只是可能会丢失 1 秒内的数据。

4、AOF重写机制(防止日志文件无限增长)

        在 Redis 中,AOF 持久化会不断记录写操作命令到一个文件中,随着时间的推移,这个文件的大小会越来越大。如果 AOF 文件太大,可能会带来一些问题,例如性能问题:文件越大,Redis 重启时需要花费更多时间去读取 AOF 文件以恢复数据,导致恢复速度变慢。

        为了解决这个问题,Redis 提供了 AOF 重写机制,当 AOF 文件超过设定的阈值后,Redis 会自动对 AOF 文件进行压缩。

(一)AOF 重写的原理:

        AOF 重写机制是在重写时,读取当前数据库中的所有键值对,然后将每一个键值对用一条命令记录到「新的 AOF 文件」,等到全部记录完后,就将新的 AOF 文件替换掉现有的 AOF 文件。所以,AOF 重写机制并不是直接修改现有的 AOF 文件,而是创建一个新的 AOF 文件,这个新的文件会根据当前 Redis 数据库的状态来生成。

  • 从数据库读取当前状态:重写时,Redis 会读取当前数据库中的所有键值对。
  • 记录最新状态:然后,每个键值对只会用一条命令记录到新的 AOF 文件中。这就避免了历史的命令积累,只记录当前的最新数据状态。

举个例子:

        假设在没有重写之前,我们执行了两条命令:

set name xiaotao

set name xiaotaostudy

        这两条命令会依次被记录到 AOF 文件中。但是在 AOF 重写之后,Redis 会只保留最新的键值对状态,即用一条命令 set name xiaotaostudy 来替换之前的两条命令。因为第一条命令已经是历史命令,最新的值已经覆盖掉它了,没必要保留。

        通过这种方式,AOF 文件的体积大大减少了,因为它只保存了数据的最终状态,而不是所有的修改历史。

重写到新的 AOF 文件中,而不是直接对旧 AOF 文件修改的好处

  • 数据安全:如果重写过程中发生了错误,比如进程挂了,现有的 AOF 文件不会被影响,因为 Redis 还没有用新的文件替换它。
  • 避免污染现有文件:如果直接修改现有文件,一旦发生错误,文件可能会损坏,无法用于数据恢复。

(2)重写期间的同步机制

        由于 AOF 重写涉及到大量的写入操作,直接在主进程中进行重写可能会影响 Redis 处理命令的效率。为了避免这种情况,Redis 将 AOF 重写的操作放在子进程中执行,主进程继续处理正常的命令请求。

  • AOF 重写缓冲区:当子进程创建新的 AOF 文件时,Redis 主进程会将所有新执行的写命令记录到一个叫做 AOF 重写缓冲区的地方。这是为了确保在重写过程中,数据的修改不会丢失。
  • 同步数据:当子进程完成新的 AOF 文件创建后,Redis 会把重写期间存放在缓冲区的写命令追加到新的 AOF 文件末尾。这确保了新文件和当前数据库的状态完全一致。
  • 文件替换:新 AOF 文件创建完成并同步后,Redis 将旧的 AOF 文件替换为新的文件,完成整个重写过程。

(三)手动或自动触发 AOF 重写

  • 手动触发:你可以通过 BGREWRITEAOF 命令手动执行 AOF 重写。

  • 自动触发:Redis 还支持自动触发 AOF 重写,通过配置以下两个参数实现:

    1. auto-aof-rewrite-min-size:AOF 文件的最小触发大小。只有当文件大小超过这个值时,才会触发重写。默认值是 64 MB。

    2. auto-aof-rewrite-percentage:AOF 文件大小增长百分比。如果当前 AOF 文件的大小相较于上一次重写后的文件大小,增加了设定的百分比值,Redis 会触发自动重写。默认是 100%,表示文件大小翻倍时重写。

推荐: 

【MySQL】常见的SQL优化方式(二)-CSDN博客icon-default.png?t=O83Ahttps://blog.csdn.net/m0_65277261/article/details/142610165?spm=1001.2014.3001.5501【MySQL】常见的SQL优化方式(一)_mysql优化-CSDN博客icon-default.png?t=O83Ahttps://blog.csdn.net/m0_65277261/article/details/142376280?spm=1001.2014.3001.5501

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值