什么是持久化:
持久化,指将数据存储到可永久保存的设备中。
例如,将内存中的数据存储到可永久保存的硬盘中。
Redis 是一个键值对数据库服务器。基于内存存储数据,它常被用做缓存数据库,用来替代 memcached
为什么要做持久化:
- Redis 基于内存存储,断电时数据会丢失
- 内存比硬盘贵得多,所以需要将一些不能丢失的数据持久化到硬盘上
- 一些特别重要的数据,是需要存到 MySQL 的。
Redis 有两种持久化方式,一种是 RDB、一种是 AOF。
RDB:就是对 Redis 中的数据进行周期性的持久化。类似于快照
AOF:就是对每一条写入、删除记录做日志,Redis 重启的时候,重启 AOF 日志重构数据集 如果同时使用两种,Redis 就会优先实现 AOF,因为数据更加完整
两种持久化方式的使用场景
Redis 是内存型数据库,一般来用作缓存。保存在内存的数据有一个特点, 就是断电消失,因此一旦 Redis 宕机了,重启以后保存在 Redis 里面的数据就会消失, 此时服务器在 Redis 里面获取不到缓存,就会让缓存无法命中,导致缓存雪崩,请求直接打到 MySQL 上最后让 MySQL 也宕机。 因此我们需要 Redis 持久化来做灾难恢复、数据恢复还有数据库高可用。
RDB 持久化
RDB:Redis database 的简称。一看这个,你就应该能猜到,这是 Redis 的默认持久化方式。
RDB 中持久化生成的是一个经过压缩的二进制文件。
RDB 持久化时机:
- 在客户端执行 SAVE 或者 BGSAVE
- 根据配置规则自动快照(稍后会讲到)
- 执行 FLUSHALL 命令
- 执行复制(replication)
RDB 持久化步骤:
- fork 复制出一个父进程的副本子进程
- 子进程将内存中的数据写入到硬盘中的临时文件
- 将临时文件替换旧的 rdb 文件
自动间隔保存(配置规则):
save 900 1 # 每900秒检查一次,如果有1条数据修改了,那么执行 rdb
save 300 10 # 每300秒检查一次,如果有10条数据修改了,那么执行 rdb
save 60 10000 # 每60秒检查一次,如果有10000条数据修改了,那么执行 rdb
RDB 文件还原
服务器启动时,会直接载入 RDB 文件。
但是如果 AOF 文件存在,则会载入 AOF 文件
AOF 持久化
AOF 是 Append Only File 的简称。
AOF 通过保存客户端传过来的写命令来记录数据库的状态
AOF 持久化的时机
需要在配置文件中加入:
appendonly yes
刷新到硬盘的时机
由于操作系统的缓存机制,每次写入到 aof 文件之后,其实是写入到了系统缓存中,默认情况下,操作系统每 30 秒同步磁盘一次
# appendfsync always # 每次执行写入都会同步, Redis 底层是基于事件的,如果事件没有处理完,而机器挂了,就会丢失一个事件的内容。所以,即使是 always 也不能保证数据不丢失。
appendfsync everysec # 默认值,每秒同步一次
# appendfsync no # 依靠操作系统的同步频率
AOF 持久化的步骤
主进程进行如文章末尾所示的三个步骤:
- 命令追加
- 文件写入
- 文件同步
AOF 重写的时机
配置:
# 当前 AOF 文件超过上次重写时的 AOF 文件大小的百分之多少时再次进行重写
# 如果之前没有冲写过,则以启动时的 AOF 文件大小为依据。
auto-aof-rewrite-percentage 100
# 允许重写的最小值
auto-aof-rewrite-min-size 64mb
主动执行 BGREWRITEAOF 命令触发 AOF 重写。
AOF 重写步骤
如果是在客户端直接执行 REWRITEAOF ,会阻塞服务,直到重写完成,将新的 AOF 文件覆盖旧的文件。这种方式一般不会考虑。
BGREWRITEAOF 命令的执行过程如文末图片所示:
1、父进程写入 AOF 缓冲区和 AOF 重写缓冲区
2、子进程执行 AOF 重写,完成之后发送信号给父进程
3、父进程收到信号将 AOF 重写缓冲区的内容写入到新的 AOF 文件中,并且覆盖原有的 AOF 文件
AOF 重写是将多条命令用一条命令代替。
如上面代码所示,存储一个 msg 使用了两条命令。经过 AOF 文件重写之后,就会变成如下所示,大大减少了使用的存储空间:
RDB: 优点:保存多份完整备份,对 IO 影响小,适合做冷备,并且在宕机后恢复更加快 缺点:一般快照文件生成的间隙在 5min,一旦宕机,就会丢失 5min 的数据。同时如果快照文件过大,会让服务暂停几毫秒甚至一秒
AOF: 优点:一般 1s 同步一次,最多丢失 1s 的数据。同步日志是使用 append-only 模式,写入快,并且日志文件不易破损,尾部破损也容易恢复。并且 AOF 文件大小不会影响性能。 缺点:AOF 日志一般比 RDB 文件大,同时以前 AOF出过 Bug导致数据没有完整的恢复。
一般我们选择的话,不能单单使用 RBD 会丢失许多数据,也不能单单使用 AOF 恢复速度比较慢,也容易有 bug。推荐同时使用,AOF 保证数据不丢失,RBD 做冷备,一旦 AOF 丢失或者不可用的时候可以用于快速恢复。