小知识,大挑战!本文正在参与“程序员必备小知识”创作活动。
我们接着上文中 AOF 的配置继续讲,要想了解接下来的配置内容,先得说一下“日志重写”的原理:
重写
由于AOF
采用的是将命令追加到文件末尾的方式,所以随着写入命令的不断增加,AOF
文件的体积会变得越来越大。为避免出现此种情况,新增了重写机制:可以在不打断服务客户端的情况下,对AOF
文件进行重建(rebuild
)。
重写触发: 通过执行bgrewriteaof
命令,可以生成一个新的AOF
文件,该文件包含重建当前数据集所需的最少命令。Redis 2.2
需手动执行该命令,Redis 2.4
则可以通过修改配置文件的方式自动触发(配置在下边涉及)。
重写原理:
Redis
执行系统函数fork()
,创建一个子进程(与主进程完全一致);- 子进程开始将新
AOF
文件的内容写入到临时文件; - 对于所有新执行的写入命令,父进程一边将它们累积到一个内存缓存中,一边将这些改动追加到现有
AOF
文件的末尾,这样即使在重写的中途发生停机,现有的AOF
文件也是安全的; - 当子进程完成重写工作时,它给父进程发送一个信号,父进程在接收到信号之后,将内存缓存中的所有数据追加到新
AOF
文件的末尾。 Redis
原子地用新文件替换旧文件,之后所有命令都会直接追加到新AOF
文件的末尾。
配置文件
no-appendfsync-on-rewrite no
当我们同时执行主进程的写操作和子进程的重写操作时,两者都会操作磁盘,而重写往往会涉及到大量的磁盘操作,这样就会造成主进程在写aof
文件的时候出现阻塞的情形。
为了解决这个问题,no-appendfsync-on-rewrite
参数出场了。
- 如果该参数设置为
no
,是最安全的方式,不会丢失数据,但是要忍受阻塞的问题; - 如果设置为
yes
,这就相当于将appendfsync
设置为no
,这说明并没有执行磁盘操作,只是写入了缓冲区。因此这样并不会造成阻塞(因为没有竞争磁盘),但是如果这个时候redis
挂掉,就会丢失数据。丢失多少数据呢?在linux
的操作系统的默认设置下,最多会丢失30s的数据。
因此,如果应用系统无法忍受延迟,而可以容忍少量的数据丢失,则设置为yes
;如果应用系统无法忍受数据丢失,则设置为no
。
auto-aof-rewrite-percentage 100
重写百分比,默认为上次重写后aof
文件大小的一倍。
auto-aof-rewrite-min-size 64mb
重写触发的最小值:64mb。
根据auto-aof-rewrite-min-size
和auto-aof-rewrite-percentage
参数确定自动触发时机。Redis
会记录上次重写时的AOF
大小,默认配置是当AOF
文件大小是上次rewrite
后大小的一倍且文件大于64M
时触发。
大型互联网公司一般都是
3G
起步
aof-use-rdb-preamble yes
在重写AOF
文件时,Redis
能够在AOF
文件中使用RDB
前导,以加快重写和恢复速度。启用此选项后,重写的AOF
文件由两个不同的节组成:RDB file
、AOF tail
加载Redis
时,会识别AOF
文件以Redis字符串开头,并加载带前缀的RDB
文件,然后继续加载AOF
尾部。
到这儿,AOF 的配置文件内容就告一段落了,下文我们来了解下 AOF 的优缺点以及两种持久化方式该如何做选择。如果你有不同的意见或者更好的idea
,欢迎联系阿Q,添加阿Q可以加入技术交流群参与讨论呦!