本文将对Redis的两种持久化方式作详细的介绍,从配置,机制,优缺点几方面讲起
Redis提供了两种持久化的选项,一种是快照文件(snapshotting,RDB),它会基于某个时间点将数据所有写入硬盘中(默认为dump.rdb
)。另外一种是只追加文件(append-only,AOF),它会在执行写入命令时将命令写入到硬盘中。linux
Redis持久化数据最主要是为了数据备份,故障恢复,也有一些通过耗时较长的计算结果存在Redis中,若是这些数据存在硬盘中,即便服务器重启了以后,这些数据仍是存在的,不用再去耗时计算了。redis
这两种方式能够单独使用,也能够结合起来使用。最重要的仍是要理解RDB和AOF的优劣势,结合本身的应用作一个权衡。服务器
save 900 1 stop-writes-on-bgsave-error yes rdbcompression yes rdbchecksum yes dbfilename dump.rdb dir ./
上面6项配置中,前5项均是RDB
的配置,最后一个是RDB
与 AOF
公用的配置app
dir ./
,指定 RDB
和 AOF
文件的路径save 900 1
, 多久执行一次快照操做, 900秒内有1次写入则执行快照操做stop-writes-on-bgsave-error
, 建立快照失败后是否依然写命令,默认为yes
rdbcompression
, 是否对快照文件进行压缩,默认为 yes
rdbchecksum
, rdb文件是否启用CRC64文件数据完整性检查,5.0版本以后的属性,默认为 yes
,开启后在 save
和 load
时将耗费 10%
的性能,能够关闭此配置来提升性能dbfilename
, rdb文件名,默认为 dump.rdb
Redis 经过建立快照的方式,得到内存中某个时间点的数据副本。Redis重启时能够从 RDB
文件上恢复数据。咱们也能够把 RDB
文件备份在别的服务器上。工具
根据上述的几个配置项,快照被写入 dir
目录下的 dbfilename
文件中。若是在新的快照文件建立完成以前,Redis服务器发生了宕机,那这期间的数据将丢失。性能
Redis中有两个命令能够建立快照文件, SAVE
和 BGSAVE
。ui
SAVE
命令后,服务器将不会再相应任何命令,直到快照文件完成。BGSAVE
命令后,Redis父进程会调用 fork
来建立一个子进程,由子进程去负责快照文件的写入,父进程则继续处理客户端的命令请求。SAVE
或者 BGSAVE
save
配置项,达到配置项的要求时,Redis会自动执行 BGSAVE
命令。该配置项能够设置多组,若是设置了多组,只要达到其中一组的要求,就会执行BGSAVE
SHUTDOWN
指令,或者接收到标准 TERM
信号时,会执行 SAVE
命令,阻塞全部客户端,直到 SAVE
命令执行完成后,关闭服务器SYNC
命令,主服务器会执行 BGSAVE
命令,而后将快照文件发给从服务器须要注意的是, 执行 BGSAVE
命令可能会形成服务器暂停几毫秒或者几秒,具体时长要根据数据量的大小以及服务器的配置来看。在数据量特别大,服务器内存吃紧的状况下,可能会形成长时间的停顿,甚至宕机。一般状况下, BGSAVE
是要比 SAVE
好一些,由于不会影响客户端的请求,不过在数据量巨大的状况下, BGSAVE
可能会比 SAVE
指令耗时更长。因此仍是要结合具体的数据状况来选择。若是能够接受数据丢失5分钟,15分钟,1小时甚至更长时间的数据的话,甚至能够关闭自动保存,由客户端决定何时来执行快照副本的建立。this
appendonly no appendfilename "appendonly.aof" appendfsync everysec no-appendfsync-on-rewrite no auto-aof-rewrite-percentage 100 auto-aof-rewrite-min-size 64mb aof-load-truncated yes aof-use-rdb-preamble yes
appendonly
,是否开启 AOF,默认为 no
appendfilename
, AOF 文件名appendfsync
① ,多久才将写入的内容同步到硬盘上,有 always
,everysec
(默认),no
三种。下面对比了三种方式的性能no-appendfsync-on-rewrite
,在重写时是否执行fsync
操做,默认为 no
auto-aof-rewrite-percentage
②, 当文件达到上一个文件的多少百分比时自动重写auto-aof-rewrite-min-size
②,自动重写的最小文件体积aof-load-truncated
③,AOF文件被截断时是否启动,默认为 yes
aof-use-rdb-preamble
④,是否支持AOF和RDB混合使用,默认为 yes
(1) 关于 appendfsync
的说明atom
选项 | 同步频率 |
---|---|
always | 每次执行写入操做都执行fsync ,这将很是影响性能,严重下降Redis的吞吐 |
everysec | 每隔1s执行一次 fsync ,显示的将多个写入命令同步到硬盘,性能很是好,若是丢失数据也只是丢失1s内的数据 |
no | 不执行 fsync ,交给操做系统去处理。通常Linux是每隔30s刷新一次数据到磁盘上,取决于内核的精准调整 |
(2) 关于 rewrite
操作系统
前面提到,AOF是将每条写入命令都同步到硬盘,包括删除key的指令,一直这么下去,AOF文件将会变的很是庞大,甚至占用全部硬盘空间。
rewrite
就是解决这个问题的,它对应的命令是 BGREWRITEAOF
, 这个命令和 BGSAVE
很是类似,都是由Redis父进程fork的子进程去执行操做,因此它和 BGSAVE
有相同的缺点。BGREWRITEAOF
会经过移除AOF中冗余命令的方式来重写AOF文件,重写以后体积就会变小不少。
auto-aof-rewrite-percentage
和 auto-aof-rewrite-min-size
这两项配置是配置自动重写AOF文件的触发条件,只有在设置了 appendonly yes
的状况下,也就是开启了AOF持久化机制才会生效。
举个例子,auto-aof-rewrite-percentage 100
, auto-aof-rewrite-min-size 64mb
表示,当AOF大于 64mb
而且比上一次重写以后的体积大了100%
才会执行BGREWRITEAOF
。能够经过修改这两项参数来控制AOF重写的频率。
(3) 关于 aof-load-truncated
在写入AOF文件的过程当中,可能会因为各类缘由(停电,磁盘空间占满,服务器故障致使Redis宕机)致使AOF写入命令被截断,若是该配置项设置为 yes
, Redis将会在重启时,清除被截断的命令以后的全部命令(一般状况下后面也没有命令了),而后正常重启。若是不想这样,能够将此项设置为 no
,Redis将会在重启时抛出错误并退出。须要注意的是:最新版本中即便设置了 no
, Redis也会将被截断的命令以后全部命令删除,以保证下次从新启动时可以正常启动,老版本中则不会,须要使用 redis-check-aof
工具来修复,具体命令是redis-check-aof --fix
如下是aof-load-truncated yes
的状况下,Redis重启时发现了AOF被截断,打出的日志
* Reading RDB preamble from AOF file... * Reading the remaining AOF tail... # !!! Warning: short read while loading the AOF file !!! # !!! Truncating the AOF at offset 439 !!! # AOF loaded anyway because aof-load-truncated is enabled
(4) 关于 aof-use-rdb-preamble
Redis4.0之后,支持AOF和RDB混合使用,能够经过此项进行配置是否开启。
AOF机制对每条写入命令做为日志,以append-only的模式写入一个日志文件中,在redis重启的时候,能够经过回放AOF日志中的写入指令来从新构建整个数据集。
Redis并不会将数据直接写入硬盘中,而是会先将数据写进linux os cache
,而后在经过配置的appendfsync
设置的时间来执行fsync
操做,强行将数据刷入磁盘文件。
AOF是存放每条的写命令,因此会不断扩大,当大到必定程度,AOF作rewrite
操做,就会基于当时redis内存中的数据,来从新构造一个更小的AOF文件,而后将旧的文件删掉。
redis-check-aof
轻松修复。Redis为咱们提供了工具,redis-check-rdb
和 redis-check-aof
具体使用方法以下:
[root@iZnom30el3gvhxZ ~]# redis-check-aof Usage: redis-check-aof [--fix] <file.aof> [root@iZnom30el3gvhxZ ~]# redis-check-rdb Usage: redis-check-rdb <rdb-file-name>
下面是官方文档中对于AOF文件损坏的一些说明,我摘了过来:
If the AOF file is not just truncated, but corrupted with invalid byte sequences in the middle, things are more complex. Redis will complain at startup and will abort:
* Reading the remaining AOF tail... # Bad file format reading the append only file: make a backup of your AOF file, then use ./redis-check-aof --fix <filename>The best thing to do is to run the
redis-check-aof
utility, initially without the--fix
option, then understand the problem, jump at the given offset in the file, and see if it is possible to manually repair the file: the AOF uses the same format of the Redis protocol and is quite simple to fix manually. Otherwise it is possible to let the utility fix the file for us, but in that case all the AOF portion from the invalid part to the end of the file may be discareded, leading to a massive amount of data lost if the corruption happen to be in the initial part of the file.How it works
Log rewriting uses the same copy-on-write trick already in use for snapshotting. This is how it works:
- Redis forks, so now we have a child and a parent process.
- The child starts writing the new AOF in a temporary file.
- The parent accumulates all the new changes in an in-memory buffer (but at the same time it writes the new changes in the old append-only file, so if the rewriting fails, we are safe).
- When the child is done rewriting the file, the parent gets a signal, and appends the in-memory buffer at the end of the file generated by the child.
- Profit! Now Redis atomically renames the old file into the new one, and starts appending new data into the new file.
How I can switch to AOF, if I'm currently using dump.rdb snapshots?
There is a different procedure to do this in Redis 2.0 and Redis 2.2, as you can guess it's simpler in Redis 2.2 and does not require a restart at all.
Redis >= 2.2
- Make a backup of your latest dump.rdb file.
- Transfer this backup into a safe place.
- Issue the following two commands:
- redis-cli config set appendonly yes
- redis-cli config set save ""
- Make sure that your database contains the same number of keys it contained.
- Make sure that writes are appended to the append only file correctly.
The first CONFIG command enables the Append Only File. In order to do so Redis will block to generate the initial dump, then will open the file for writing, and will start appending all the next write queries.
The second CONFIG command is used to turn off snapshotting persistence. This is optional, if you wish you can take both the persistence methods enabled.
IMPORTANT: remember to edit your redis.conf to turn on the AOF, otherwise when you restart the server the configuration changes will be lost and the server will start again with the old configuration.
Redis 2.0
- Make a backup of your latest dump.rdb file.
- Transfer this backup into a safe place.
- Stop all the writes against the database!
- Issue a redis-cli bgrewriteaof. This will create the append only file.
- Stop the server when Redis finished generating the AOF dump.
- Edit redis.conf end enable append only file persistence.
- Restart the server.
- Make sure that your database contains the same number of keys it contained.
- Make sure that writes are appended to the append only file correctly.
经过以上内容,应该已经对RDB和AOF两种方式的优缺点有了大概的了解,具体如何选择,还需根据本身的业务状况来选择,这里给出的意见是两种一块儿用,条件容许的话,将持久化的文件时常备份到多台不一样的服务器上。
Redis4.0之后,支持AOF和RDB混合使用,在 redis.conf
中经过 aof-use-rdb-preamble yes
设置。
更多详细内容参考: