Redis存储配置数据持久化,开启aof后,配置了aof重写规则,但aof文件仍然持续增长,当aof数据文件增长过大时,需要进行手动清理。本文意为手动清理aof文件提供帮助。同时对rdb和aof数据存储进行说明。
1. Redis数据持久化介绍
1.1. RDB数据存储
RDB(Redis Database) 通过快照的形式将数据保存到磁盘中。所谓快照,可以理解为在某一时间点将数据集拍照并保存下来。Redis 通过这种方式可以在指定的时间间隔或者执行特定命令时将当前系统中的数据保存备份,以二进制的形式写入磁盘中,默认文件名为dump.rdb。
RDB 的触发有三种机制,执行save命令;执行bgsave命令;在redis.config中配置自动化。
save 触发
Redis是单线程程序,这个线程要同时负责多个客户端套接字的并发读写操作和内存结构的逻辑读写。而save命令会阻塞当前的Redis服务器,在执行该命令期间,Redis无法处理其他的命令,直到整个RDB过程完成为止,用一张图描述以下:
当这条指令执行完毕,将RDB文件保存下来后,才能继续去响应请求。这种方式用于新机器上数据的备份还好,如果用在生产上,那么简直是灾难,数据量过于庞大,阻塞的时间点过长。这种方式并不可取。
bgsave 触发
为了不阻塞线上的业务,那么Redis就必须一边持久化,一边响应客户端的请求。所以在执行bgsave时可以通过fork一个子进程,然后通过这个子进程来处理接下来所有的保存工作,父进程就可以继续响应请求而无需去关心I/O操作。该模式为redis默认数据落盘保存模式。
redis.config 配置
上述两种方式都需要我们在客户端中去执行save或者bgsave命令,在生产情况下我们更多地需要是自动化的触发机制,那么Redis就提供了这种机制,我们可以在redus.config中对持久化进行配置:
像上述这样在redis.config中进行配置,如save 900 1 是指在 900 秒内,如果有一个或一个以上的修改操作,那么就自动进行一次自动化备份;save 300 10同样意味着在 300 秒内如果有十次或以上的修改操作,那么就进行数据备份,依次类推。
如果你不想进行数据持久化,只希望数据在redis运行时存在于内存中,那么你可以通过 save ""禁止掉数据持久化。
RDB 持久化相关的系数
- stop-writes-on-bgsave-error:默认值为yes,即当最后一次 RDB 持久化保存文件失败后,拒绝接收数据。这样做的好处是可以让用户意识到数据并没有被成功地持久化,避免后续更严重的业务问题的发生;
- rdbcompression:默认值为yes,即代表将存储到磁盘中的快照进行压缩处理;
- rdbchecksum:默认值为yes,在快照存储完成后,我们还可以通过CRC64算法来对数据进行校验,这会提升一定的性能消耗;
- dbfilename:默认值为dump.rdb,即将快照存储命名为dump.rdb;
- dir:设置快照的存储路径。
RDB的优势以及它的劣势:
- 优势:
RDB 是一个非常紧凑(compact)的文件(保存二进制数据),它保存了 Redis 在某个时间点上的数据集。 这种文件非常适合用于进行备份: 比如说,你可以在最近的 24 小时内,每小时备份一次 RDB 文件,并且在每个月的每一天,也备份一个 RDB 文件。 这样的话,即使遇上问题,也可以随时将数据集还原到不同的版本;RDB 非常适用于灾难恢复(disaster recovery):它只有一个文件,并且内容都非常紧凑,可以(在加密后)将它传送到别的数据中心;RDB 可以最大化 Redis 的性能:父进程在保存 RDB 文件时唯一要做的就是 fork 出一个子进程,然后这个子进程就会处理接下来的所有保存工作,父进程无须执行任何磁盘 I/O 操作;RDB 在恢复大数据集时的速度比 AOF 的恢复速度要快。
- 劣势:
如果业务上需要尽量避免在服务器故障时丢失数据,那么 RDB 并不适合。 虽然 Redis 允许在设置不同的保存点(save point)来控制保存 RDB 文件的频率, 但是, 由于 RDB 文件需要保存整个数据集的状态, 所以这个过程并不快,可能会至少 5 分钟才能完成一次 RDB 文件保存。 在这种情况下, 一旦发生故障停机, 就可能会丢失好几分钟的数据。每次保存 RDB 的时候,Redis 都要 fork() 出一个子进程,并由子进程来进行实际的持久化工作。 在数据集比较庞大时, fork() 可能会非常耗时,造成服务器在某某毫秒内停止处理客户端; 如果数据集非常巨大,并且 CPU 时间非常紧张的话,那么这种停止时间甚至可能会长达整整一秒。 虽然 AOF 重写也需要进行 fork() ,但无论 AOF 重写的执行间隔有多长,数据的耐久性都不会有任何损失。
1.2. AOF数据存储
RDB 持久化是全量备份,比较耗时,所以Redis就提供了一种更为高效地AOF(Append Only-file)持久化方案,简单描述它的工作原理:AOF日志存储的是Redis服务器指令序列,AOF只记录对内存进行修改的指令记录。
在服务器重新启动时,Redis就会利用 AOF 日志中记录的这些操作从新构建原始数据集。
Redis会在收到客户端修改指令后,进行参数修改、逻辑处理,如果没有问题,就立即将该指令文本存储到 AOF 日志中,也就是说,先执行指令才将日志存盘。这点不同于 leveldb、hbase等存储引擎,它们都是先存储日志再做逻辑处理。
AOF也有不同的触发方案,这里简要描述以下三种触发方案:
- always:每次发生数据修改就会立即记录到磁盘文件中,这种方案的完整性好但是IO开销很大,性能较差;
- everysec:在每一秒中进行同步,速度有所提升。但是如果在一秒内宕机的话可能失去这一秒内的数据;
- no:默认配置,即不使用 AOF 持久化方案。可以在redis.config中进行配置,appendonly no改换为yes,再通过注释或解注释appendfsync配置需要的方案:
AOF 重写机制
随着Redis的运行,AOF的日志会越来越长,如果实例宕机重启,那么重放整个AOF将会变得十分耗时,而在日志记录中,又有很多无意义的记录,比如我现在将一个数据 incr 一千次,那么就不需要去记录这1000次修改,只需要记录最后的值即可。所以就需要进行 AOF 重写。
Redis 提供了bgrewriteaof指令用于对AOF日志进行重写,该指令运行时会开辟一个子进程对内存进行遍历,然后将其转换为一系列的 Redis 的操作指令,再序列化到一个日志文件中。完成后再替换原有的AOF文件,至此完成。
同样的也可以在redis.config中对重写机制的触发进行配置:
- no-appendfsync-on-rewrite设置为yes,开启重写机制;
- auto-aof-rewrite-percentage 100意为比上次重写后文件大小增长了100%再次触发重写(默认为100%);
- auto-aof-rewrite-min-size 64mb意为当文件至少要达到64mb才会触发制动重写(默认64mb)。
重写也是会耗费资源的,所以当磁盘空间足够的时候,这里可以将 64mb 调整更大些,降低重写的频率,达到优化效果。
补充:appendfilename 设置aof文件名称。
AOF 的优劣
- AOF 持久化的默认策略为每秒钟 fsync 一次,在这种配置下,Redis 仍然可以保持良好的性能,并且就算发生故障停机,也最多也只会丢失掉一秒钟内的数据;
- AOF 文件是一个只进行追加操作的日志文件(append only log), 因此对 AOF 文件的写入不需要进行 seek , 即使日志因为某些原因而包含了未写入完整的命令(比如写入时磁盘已满,写入中途停机,等等), redis-check-aof 工具也可以轻易地修复这种问题。
- Redis 可以在 AOF 文件体积变得过大时,自动地在后台对 AOF 进行重写: 重写后的新 AOF 文件包含了恢复当前数据集所需的最小命令集合。 整个重写操作是绝对安全的,因为 Redis 在创建新 AOF 文件的过程中,会继续将命令追加到现有的 AOF 文件里面,即使重写过程中发生停机,现有的 AOF 文件也不会丢失。 而一旦新 AOF 文件创建完毕,Redis 就会从旧 AOF 文件切换到新 AOF 文件,并开始对新 AOF 文件进行追加操作。
- AOF 文件有序地保存了对数据库执行的所有写入操作, 这些写入操作以 Redis 协议的格式保存, 因此 AOF 文件的内容非常容易被人读懂, 对文件进行分析(parse)也很轻松。 导出(export) AOF 文件也非常简单: 举个例子, 如果你不小心执行了 FLUSHALL 命令, 但只要 AOF 文件未被重写, 那么只要停止服务器, 移除 AOF 文件末尾的 FLUSHALL 命令, 并重启 Redis , 就可以将数据集恢复到 FLUSHALL 执行之前的状态。
AOF 的缺点
- 对于相同的数据集来说,AOF 文件的体积通常要大于 RDB 文件的体积。
- 根据所使用的 fsync 策略,AOF 的速度可能会慢于 RDB 。 在一般情况下, 每秒 fsync 的性能依然非常高, 而关闭 fsync 可以让 AOF 的速度和 RDB 一样快, 即使在高负荷之下也是如此。 不过在处理巨大的写入载入时,RDB 可以提供更有保证的最大延迟时间(latency)。
- AOF 在过去曾经发生过这样的 bug : 因为个别命令的原因,导致 AOF 文件在重新载入时,无法将数据集恢复成保存时的原样。
2. AOF数据文件清理
2.1. 清理生成的aof文件
通过redis-cli命令登入到redis服务内存中,使用“config get dir”获取当前aof文件生成位置,输出结果即为aof文件所在路径(也可以查看redis.conf配置文件获取aof文件所在路径)。
【通过redis-cli命令登入到redis服务内存中,使用config get *aof*可以查找关于aof的相关配置(也可以查看redis.conf配置文件获取)。】
默认aof的文件名为appendonly.aof,将该文件备份拷贝到其他位置或主机,然后删除该文件。
2.2. 重新生成aof最新文件
通过redis-cli命令登入到redis服务内存中,使用bgrewriteaof重新手动生成appendonly.aof文件(防止之前被清理的数据丢失)。
2.3. 回滚
清理数据后,发现redis数据丢失,则将原来备份的aof文件重新拷贝到原有路径,重新启动redis服务,即可完成数据重新加载。
2.4. 注意事项
该清理方法无需停机,只要按照步骤执行即可,为了保证aof正常保存切记在清理后使用bgrewriteaof重新生成appendonly.aof文件。
标签:文件,持久,AOF,redis,Redis,介绍,aof,RDB From: https://blog.51cto.com/u_13482808/7267338