当前位置:主页 > 查看内容

redis持久化

发布时间:2021-04-26 00:00| 位朋友查看

简介:1、为什么redis要持久化 将redis作为数据库来使用 将redis作为写缓冲读缓冲不需要持久化 当redis崩溃crash时可以很快从磁盘恢复数据否则会引起缓存雪崩 ? 2、持久化概述 redis支持RDB和AOF两种持久化方式。 redis.conf中可配置RDB持久化文件和AOF持久化文件……

1、为什么redis要持久化?

  1. 将redis作为数据库来使用;
  2. 将redis作为写缓冲(读缓冲不需要持久化);
  3. 当redis崩溃(crash)时,可以很快从磁盘恢复数据,否则会引起缓存雪崩;

?

2、持久化概述

redis支持RDB和AOF两种持久化方式。

redis.conf中可配置RDB持久化文件和AOF持久化文件的位置和文件名。

# 持久化文件位置
dir ./
# 快照文件名
dbfilename dump.rdb
# AOF文件名
appendfilename appendonly.aof

RDB通过快照完成持久化,发生快照的条件如下:

  • 根据配置规则自动快照;
  • 用户执行save或bgsave命令;
  • 执行flushall;
  • 主从复制;

redis启动后会读取RDB文件。

redis允许同时开启RDB和AOF,redis重启后会使用AOF文件恢复数据,因为AOF方式可能丢失的数据更少。

?

3、RDB方式

3.1、自动快照

默认的redis.conf中有如下配置

#?每900秒有一个或一个以上的键被更改则进行快照,多个save之间是或的关系
save 900 1?
save 300 10
save 60 10000

自动快照是异步的,并不会阻塞客户端请求。

?

3.2、save或bgsave

save命令是同步操作,阻塞所有客户端请求,生产上避免使用。

bgsave后台异步执行,响应客户端请求,执行bgsave会立即返回OK,想知道快照是否完成可以通过lastsave命令查看最后一次快照时间。

?

3.3、flushall

执行flushall时,只要自动快照条件不为空,无论是够满足自动快照条件,都会进行一次快照。

?

3.4、快照原理

  1. redis使用fork函数复制一份当前进程(父进程)的副本(子进程)
  2. 父进程继续接收并处理客户端请求,而子进程将内存数据写入磁盘中的临时文件
  3. 当子进程写完所有数据后用临时文件替换旧的RDB文件

在执行fork函数时操作系统(类Unix系统)会使用写时复制(copy-on-write)策略,即fork函数发生的一刻父子进程共享同一内存数据,当父进程要更改其中某片数据时(如执行一个命令),操作系统会将该片数据复制一份以保证子进程的数据不受影响,因此新的RDB文件存储的是执行fork函数一刻的内存数据。

?

4、AOF方式

AOF会将redis执行的每一条写命令追加到磁盘文件中。

默认情况下redis没有开启AOF,可通过如下配置开启。

appendonly yes

AOF文件中保存的就是redis通信协议的内容。

比如我执行一条set age 10命令,则AOF文件内容如下。

*3
$3
set
$3
age
$2
10

?

4.1、优化AOF文件

比如执行了两条命令set age 10和set age 12,其实AOF只用保存第二条命令就行了,因为第二条命令会覆盖第一条命令。

如果冗余命令过多,会导致AOF文件过大而内存数据并没有多少,针对这种情况每达到一定条件(见如下配置)时redis会对AOF文件进行重写。

# 当前AOF文件大小超过上一次重写的AOF文件大小的百分之多少时就重写
auto-aof-rewrite-percentage 100 
# 允许重写的最小AOF文件大小
auto-aof-rewrite-min-size 64mb 

也可以执行bgrewriteaof命令手动重写。

即使BGREWRITEAOF执行失败,也不会有任何数据丢失,因为旧的AOF文件在BGREWRITEAOF 成功之前不会被修改。

AOF重写过程:

  1. 从主进程中fork出子进程,并拿到fork时的AOF文件数据写到一个临时AOF文件中;
  2. 在重写过程中,redis收到的命令会同时写到AOF缓冲区和重写缓冲区中,这样保证重写不丢失重写过程中的命令;
  3. 重写完成后通知主进程,主进程会将AOF缓冲区中的数据追加到子进程生成的文件中;
  4. redis会原子的将旧文件替换为新文件,并开始将数据写入到新的aof文件上;

?

4.2、同步磁盘数据

AOF持久化会将命令记录在AOF文件中,但由于操作系统的缓存限制,数据并没有真正写入磁盘,而是进行了系统的磁盘缓存,默认情况下系统每30秒进行一次同步,如果这30秒期间系统异常退出则会导致数据丢失。

可通过如下配置设置同步时机。

# 总是同步
appendfsync always
# 每秒同步一次(默认)
appendfsync everysec
# 由操作系统决定(30秒)
appendfsync no

?

5、设置了过期时间的key会持久化吗?

现有如下操作

set age 10

expire age 60

save

ttl age? --50

shutdown nosave

--过10秒

./redis-server

ttl age --显示40 or 50?

正确答案是10,说明expire记录的是一个时间戳,即使redis服务停止了,停止期间这10秒的时间仍然是有效的

?

?

;原文链接:https://blog.csdn.net/xl_1803/article/details/115413924
本站部分内容转载于网络,版权归原作者所有,转载之目的在于传播更多优秀技术内容,如有侵权请联系QQ/微信:153890879删除,谢谢!

推荐图文


随机推荐