nainai1 发表于 2015-11-12 13:44:43

Redis数据持久化

Redis数据持久化      RDB方式与AOF方式,可以单独用一种或两种结合。RDB方式相当于定时全备,AOF方式相当于重做日志。REDIS在RDB与AOF都开启的情况下,启动的时候会加载AOF,因为AOF持久化方式可能丢失的数据更少。
RDB方式    这种持久化是通过快照完成的,当符合一定条件时Redis会自动将内存中的所有数据进行快照,并存储在硬盘上。    进行快照的条件由两个参数构成:save <seconds> <changes>    多个save条件之间是“或”的关系,seconds与changes之间是“与”的关系。    当条件为真,块照会被触发,然后在dir参数定义的目录,以dbfilename参数定义的文件名(一般是dump.rdb)保存下来。    举例:    save 900 1         #900秒内1个key被改动    save 300 10       #300秒内10个key被改动    save 60 10000   #60秒内10000个key被改动    时间最大的一个save后必须是1,假如是比1大的值,比如2,那么只要我每900秒内只改动1个key,那么就永远不会触发快照。    如果想取消这种持久化方式,所有SAVE参数删除或用一条save &quot;&quot;即可。
快照过程:1. Redis函数使用fork函数赋值一份当前进程的副本(子进程);2.父进程继续接收并处理客户端发来的命令,而子进程开始将内存中的数据写入硬盘中的临时文件;3.当子进程写完所有数据后,会用临时文件替换RDB文件,至此一次快照操作完成。
注意:

[*]只有快照结束才会将旧的文件替换成新,所以任何时候RDB文件都是完整可用的。
[*]新的RDB文件是开始执行fork一刻的内存数据。
[*]RDB文件是经过压缩的,可以通过配置rdbcompression参数为no以禁用压缩、以节省CPU资源,压缩后的文件更小更利于传输。
[*]可以手动用SAVE命令或BGSAVE命令让Redis执行快照,前者由主线程做快照会堵塞其他请求,后者通过fork出子进程进行。
[*]Redis启动后会读取RDB快照文件,将数据从硬盘载入内存,一般一千万个string,1G的快照需要20-30秒。
查看fork出的子进程$ redis-cli -p 6389 -a pass1234 bgsave && ps -ef | grep redisBackground saving startedldh 31080 30072 0 11:46 pts/3 00:00:00 redis-server *:6389ldh 31304 31080 0 11:53 pts/3 00:00:00 redis-rdb-bgsave *:6389
AOF方式    开启AOF持久化后,每执行一条会更改Redis中数据的命令,Redis就会将该命令写入硬盘中的AOF文件。这种写是异步的,通过后台进程处理。默认情况下AOF方式没有开启,可以通过appendonly参数设为yes来开启。AOF文件的保存位置和RDB文件位置相同,都是通过dir参数设置的,默认的文件名是appendonly.aof,可以通过appendfilename参数修改。    事实上,appendonly.aof是纯文本格式,打开后也能轻易看懂我们做过的操作。随着执行命令的增多,AOF文件会变得越来越大。所以我们希望删除其中没用的条目。例如set foo 1set foo 2set foo3第3条的效果会覆盖前两条,我们只需要保留第三条即可。实际上,我们通过设置这两个参数,来使文件达到条件就自动重写。auto-aof-rewrite-percentage 100auto-aof-rewrite-min-size 64mb实例启动后,会记得首次rewrite完后文件大小。例如是100mb,那么下次要到200mb,我们才超出100%,才会rewrite。如果实例启动以来还没rewrite过,那么启动时文件多大,就作为上次rewrite数。这里为了防止文件太小也rewrite,例如上次是10mb,这次到了20mb就rewrite,规定了必须得到64mb以上才能进行rewrite操作。将percentage设为0,可以禁用rewrite特性。其实rewrite的时候,调用的命令是BGREWRITEAOF,我们也可以手工调用它来执行rewrite。rewrite完后,冗余的数据就被删除了。启动时,redis会将AOF文件中的每条命令载入内存,可以想象,速度肯定比RDB会慢一些。
缓存同步上述所谓的写到条目写到aof文件,往往其实只是写到OS的缓存。默认情况下系统30秒执行一次同步操作,以便将缓存真正写入磁盘。难道我们AOF必须忍受最高30秒内的数据损失?我们通过appendfsync参数设置同步时机。在一定时机,redis会用fsync()系统调用来通知系统将缓存同步到磁盘。# appendfsync always--aof文件每有写入就通知系统同步缓存appendfsync everysec--每秒,安全性与快捷性的折衷# appendfsync no      --交给OS自己决定同步缓存时机






         版权声明:本文为博主原创文章,未经博主允许不得转载。
页: [1]
查看完整版本: Redis数据持久化