Redis的持久化包含两种方式:RDB和AOF
RDB
RDB是一个压缩的二进制文件,它记录了数据库在某一时刻的状态。
RDB文件可以手动生成,也支持自动生成。
-
手动生成
-
save 会阻塞redis进程知道生成RDB文件,生成期间,不能处理client过来的请求。
-
bgsave fork一个子进程来执行RDB的生成逻辑,生成期间,父进程(服务器进程)可以继续处理来自client的请求。
-
自动生成
-
通过配置save 900 1来配置自动生成,表示当满足900s内至少有一次写命令时要执行RDB生成。
RDB载入
redis服务启动时,会自动加载RDB文件,还原数据库状态。
note:当有AOF和RDB同时存在时,由于AOF文件更新一般比RDB及时,因此redis会优先使用AOF文件来还原数据状态。
AOF
AOF是通过向文件中不断追加redis服务器执行的写命令来记录数据库状态的。
AOF过程包含三步:
- 将命令写入AOF缓冲区
- 将AOF缓冲区中的命令写入AOF文件(操作系统的文件缓存)
- 将AOF文件执行同步,真正的flush到磁盘。
现代的操作系统一般都有文件系统缓存的概念。当用户将内容写入文件时,其实只是写入了文件系统缓存,还是有丢失风险的,但是性能要好的多。操作系统会根据时间或者当文件系统缓存满了的情况下来触发flush到硬盘的操作。用户也可以主动触发。这里第二步其实就是写入操作系统文件缓存。
根据appendfsync的配置不同,redis会执行不同的操作,性能也会有所差别。
-
always 每次都会写入并且同步至AOF文件
-
性能最差,安全性最高
-
everysec 每次都会写入,每隔1s同步
-
性能与安全性折中,也是默认的方案
-
no 每次只负责写入,具体的同步策略完全交给操作系统
-
性能最好,安全性最差
AOF重写
随着时间的推移,AOF文件会越来越大,原因有两个,一是本身命令不够精简;二是出现了冗余命令。此时,redis会执行AOF重写的功能。
AOF重写并不是通过原先的AOF文件来分析生成新的AOF文件。而是直接根据当前的数据库状态来生成新的AOF文件。
由于AOF文件的重写也是异步的,是不阻塞redis服务进程的。因此AOF重写的过程中,redis还在执行新的写命令,这会导致重写后的AOF文件与当时的数据库状态不一致。这个是通过一个AOF重写缓冲区来实现的。每次执行写命令时,redis都会把这个写命令记录到AOF重写缓冲区中。当AOF重写执行结束时,redis会将重写缓冲区中的命令追加到新的AOF文件中。到此,新的AOF文件与数据库状态完全一致。接下来,redis会将新的AOF文件原子的覆盖原先的AOF文件。结束。
优缺点比对:
-
AOF
-
优点
-
更及时,数据丢失情况更安全
-
缺点
-
性能稍差,尤其是always模式
-
RDB
-
优点
-
还原数据库状态更迅速