首页 > 代码库 > redis持久化详解

redis持久化详解

redis持久化详解

redis是一个支持持久化的内存型数据库,

由于是在内存中,即使有主从,数据冗余备份,也难保数据丢失,

redis持久化就是解决这个问题。

redis持久化,是通过把内存里的数据同步到磁盘上来保证持久化。

redis有两种持久化方式

一种是快照,snapshotting,也是默认方式,还有一种是只追加文件,缩写aof(apppend-only-file)。

快照(snapshotting):将某一时刻的所有数据都写入硬盘。

只追加文件(AOF):在执行写命令时,将被执行的写命令复制到硬盘里。

snapshotting(RDB)机制

创建快照有两个命令BGSAVE,SAVE。

BGSAVE过程:

1redis通过fork产生子进程

2父进程继续处理client请求,子进程负责将快照写入硬盘

3子进程写完后,用临时文件代替原来快照文件,然后子进程退出

SAVE过程:

1redis服务器停止接受来自client请求

2在快照创建完成之前将不再响应其他命令。

SAVE和BGSAVE优缺点:

save缺点:快照操作完成之前不再响应其他命令。

save优点:在大数据量的情况下,比bgsave更快速稳定。

运用场景:SAVE一般用在机器没有足够内存执行BGSAVE

               或是接收到SHUTDOWN关机命令请求时用。

               比如写个脚本,在凌晨3点访问量很小的时候,执行save快照操作。

bgsave缺点:在大数据量的情况下,BGSAVE的子进程由于要把内存里的数据写入到硬盘,

                    子进程会耗费越来越多时间。

                    如果达到十几GB数据量的话,BGSAVE可能会导致系统长时间的停顿

bgsave优点:快照操作时不影响redis服务器继续接受请求,做出响应。

运用场景:非十几GB的大数据量情况下都适合。

快照snapshotting配置选项

编辑redis.conf

save 60 1000 

//多久执行一次bgsave自动快照操作,当满足 60秒之内有1000次写入即触发。

save 3600 1      

//该条配置可以有多个,任意一个满足一次,执行一次。一小时之内只要有一条写操作就执行快照操作

stop-writes-on-bgsave-error no  

//创建快照失败后是否继续写操作

rdbcompression yes              

//是否对快照文件压缩

dbfilename dump.rdb         

//快照写入文件的名称

dir ./                                  

//快照文件的指定路径

snapshotting快照持久化运用场景

快照是将某一时间点在内存里的数据进行写入操作到硬盘。

也就是说在本次快照操作完成之后,

下一次时间点快照操作到来之前的这段时间内发生系统崩溃,

或是硬件问题,这段时间内产生的数据将会丢失。

所以快照适合对小数据丢失有一定容忍的应用和场景。

1购物车(查询简单|经常变更|数据量级不大|弱化事务|安全级别低)

2促销活动规则(存储) |  抢购  缓冲队列 

3和钱无关,支付,银行


append-only-file(AOF)机制

AOF持久化会将被执行的写命令追加到原来的AOF文件末尾,

因此redis只要重新执行一遍AOF文件包含的所有写命令

即可恢复AOF文件所记录的数据集。

1redis产生fork子进程。

2父进程继续处理client请求,子进程把aof内容写入缓冲区。

3子进程写完退出,父进程接受退出消息,将缓冲区内容写入AOF文件。


AOF配置选项

编辑redis.conf

appendonly no          

//是否启用aof方式

appendfsync everysec|always|no    

//aof文件同步频率 everysec 每秒执行同步一次,显示的将多个命令同步到硬盘,也是redis推荐的一

//个。always每个redis写命令都要同步写入到硬盘,io操作频繁影响到redis速度。但是数据最安全的一

//个。no让操作系统来决定何时该同步。

                                                       

no-appendfsync-on-rewite no         

//再对aof进行压缩的时候是否执行同步操作

auto-aof-rewrite-percentage 50      

//当aof文件大于80MB时并且AOF文件比

auto-aof-rewrite-min-size 80mb      

//上次重写之后体积大了50%,redis将自动执行BGREWRITEAOF命令,


AOF缺陷--aof文件体积问题

    表面上看,aof方式既可以把数据丢失降低到1秒(设置成appendfsync   everysec),又可以极短时间完成持久化操作,无疑是最好的方式,但是aof有文件过大的问题。随着redis不断运行,执行的写操作越来越多,aof文件不断追加命令,aof文件将越来越大,极端情况可以用完整个硬盘。另一方面,如果系统崩溃了,在机器重启后需要执行aof文件来恢复丢失数据,aof文件过大,导致,执行时间会很长。

    为了解决这个问题,就不得不说BGREWRITEAOF命令,

该命令可以移除原有aof文件里冗余的写操作重写aof文件。但是BGREWRITEAOF命令又出现了快照方式BGSAVE问题,执行BGREWRITEAOF,redis会创建子进程,子进程负责文件重写,由此带来的子进程的性能和时间问题同样存在。

无论使用aof方式还是快照方式来实现持久化都是各有利弊,选用时要因地制宜。

如果有不同见解欢迎大家一起来讨论,共同进步@_@。






观点有参考Josiah L,carlson 所著redis in action。


本文出自 “心有猛虎,细嗅蔷薇” 博客,转载请与作者联系!

redis持久化详解