Redis是一个键值对数据库服务器,服务器中通常包含着任意个非空数据库,而每个非空数据库中又可以包含任意个键值对,为了方便起见,我们将服务器中的非空数据库以及它们的键值对统称为数据库状态。

因为Redis是内存数据库,它将自己的数据库状态储存在内存里面,所以如果不想办法将储存在内存中的数据库状态保存到磁盘里面,那么一旦服务器进程退出,服务器中的数据库状态也会消失不见。为了解决这个问题,Redis提供了RDB持久化功能,这个功能可以将Redis在内存中的数据库状态保存到磁盘里面,避免数据意外丢失。

RDB持久化功能所生成的RDB文件是一个经过压缩的二进制文件,通过该文件可以还原生成RDB文件时的数据库状态。

1、RDB文件的创建与载入

有两个Redis命令可以用于生成RDB文件,一个是SAVE,另一个是BGSAVE.

SAVE命令会阻塞Redis服务器进程,直到RDB文件创建完毕为止,在服务器进程阻塞期间,服务器不能处理任何命令请求:

redis> SAVE     //等待直到RDB文件创建完毕

OK

和SAVE命令直接阻塞服务器进程的做法不同,BGSAVE命令会派生出一个子进程,然后由子进程负责创建RDB文件,服务器进程(父进程)继续处理命令请求:

redis> BGSAVE   //派生子进程,并由子进程创建RDB文件

Background saving started

和使用SAVE命令或者BGSAVE命令创建RDB文件不同,RDB文件的载入工作是在服务器启动时自动执行的,所以Redis并没有专门用于载入RDB文件的命令,只要Redis服务器在启动时检测到RDB文件存在,它就会自动载入RDB文件。服务器在载入RDB文件期间,会一直处于阻塞状态,直到载入工作完成为止。

另外值得一提的是,因为AOF文件的更新频率通常比RDB文件的更新频率高,所以:

  • 如果服务器开启了AOF持久化功能,那么服务器会优先使用AOF文件来还原数据库状态。
  • 只有在AOF持久化功能处于关闭状态时,服务器才会使用RDB文件来还原数据库状态。

2、自动间隔性保存

因为BGSAVE命令可以在不阻塞服务器进程的情况下执行,所以Redis允许用户通过设置服务器配置的save选项,让服务器每隔一段时间自动执行一次BGSAVE命令。

用户可以通过save选项设置多个保存条件,但只要其中任意一个条件被满足,服务器就会执行BGSAVE命令。

举个例子,如果我们向服务器提供以下配置:

save 900 1           #900秒 1次修改

save 300 10         #300秒 10次修改

save 60 10000     #60秒 10000次修改

那么只要满足以上三个条件中的任意一个,BGSAVE命令就会被执行。

--------------------------------------------------------------------------------------------------

AOF持久化:

除了RDB持久化功能之外,Redis还提供了AOF(Append Only File)持久化功能。与RDB持久化通过保存数据库中的键值对来记录数据库状态不同,AOF持久化是通过保存Redis服务器所执行的写命令来记录数据库状态的。

举个例子,如果我们对空白的数据库执行以下写命令,那么数据库中将包含一个键值对:

redis> SET wjoyxt "hello"

OK

RDB持久化保存数据库状态的方法是将wjoyxt键的键值对保存到RDB文件中,而AOF持久化保存数据库状态的方法则是将服务器执行的SET命令保存到AOF文件中。

被写入AOF文件的所有命令都是以Redis的命令请求协议格式保存的,因为Redis的命令请求协议是纯文本格式,所以我们可以直接打开一个AOF文件,观察里面的内容。

服务器在启动时,可以通过载入和执行AOF文件中保存的命令来还原服务器关闭之前的数据库状态。

AOF持久化功能的实现可以分为命令追加(append)、文件写入、文件同步(sync)三个步骤。

当AOF持久化功能处于打开状态时,服务器在执行完一个写命令之后,会以协议格式将被执行的写命令追加到服务器状态的aof_buf缓冲区的末尾。

文件的写入和同步:

为了提高文件的写入效率,在现代操作系统中,当用户调用write函数,将一些数据写入到文件的时候,操作系统通常会将写入数据暂时保存在一个内存缓冲区里面,等到缓冲区的空间被填满、或者超过了指定的时限之后,才堤地将缓冲区中的数据写入到磁盘里面。

这种做法虽然提高了效率,但也为写入数据带来了安全问题,因为如果计算机发生停机,那么保存在内存缓冲区里面的写入数据将会丢失。

为此,系统提供 了fsync和fdatasync两个同步函数,它们可以强制让操作系统立即将缓冲区中的数据写入到硬盘里面,从而确保写入数据的安全性。

AOF持久化的效率和安全性:

服务器配置 appendfsync 选项的值直接决定AOF持久化功能的效率和安全性。

  • 当appendfsync的值为always时,服务器在每个事件循环都要将aof_buf缓冲区中的所有内容写入到AOF文件,并且同步AOF文件,所以always的效率是appendfsync选项三个值当中最慢的一个,但从安全性来说,always也是最安全的,因此即使出现故障停机,AOF持久化也只会丢失一个事件循环中所产生的命令数据。
  • 当appendfsync的值为everysec时,服务器在每个事件循环都要将aof_buf缓冲区中的所有内容写入到AOF文件,并且每隔一秒就要在子线程中对AOF文件进行一次同步。从效率上来讲,everysec模式足够快,并且就算出现故障停机,数据库也只丢失一秒钟的命令数据。在性能和持久化方面做了很好的折中,是受推荐的方式。
  • 当appendfsync的值为no时,服务器在每个事件循环都要将aof_buf缓冲区中的所有内容写入到AOF文件,至于何时对AOF文件进行同步,则由操作系统控制。因为处于no模式下的flushAppendOnlyFile调用无须执行同步操作,所以该模式下的AOF文件写入速度总是最快的,不过因为这种模式会在操作系统缓存中积累一段时间的写入数据,所以该模式的单次同步时长通常是三种模式中时间最长的。从平摊操作的角度来看,no模式和everysec模式的效率类似,当出现故障停机时,使用no模式的服务器将丢失上次同步AOF文件之后的所有写命令数据。

AOF文件的载入与数据还原:

因为AOF文件里面包含了重建数据库状态所需的所有写命令,所以服务器只要读入并重新执行一遍AOF文件里面保存的写命令,就可以还原服务器关闭之前的数据库状态。

但是随着服务器运行时间的流逝,AOF文件中的内容会越来越多,文件的体积也会越来越大,如果不加以控制的话,体积过大的话AOF文件很可能对Redis服务器、甚至整个宿主计算机造成影响,并且AOF文件的体积越大,使用AOF文件来进行数据还原所需的时间就越多。

为了解决AOF文件体积膨胀的问题,Redis提供了AOF文件重写(rewrite)功能。通过该功能,Redis服务器可以创建一个新的AOF文件来替代现有的AOF文件,新旧两个AOF文件所保存的数据库状态相同,但新的AOF文件的体积通常会比旧AOF文件的体积要小得多。

AOF文件重写的实现:

虽然Redis将生成新AOF文件替换旧AOF文件的功能命名为"AOF文件重写",但实际上,AOF文件重写并不需要对现有的AOF文件进行任何读取、分析或者写入操作,这个功能是通过读取服务器当前的数据库状态来实现的。首先从数据库中读取键现在的值,然后用一条命令去记录键值对,代替之前记录这个键值对的多条命令,用新AOF文件覆盖旧AOF文件,这就是AOF重写功能的实现原理。

AOF文件后台重写过程:    redis> BGREWRITEAOF

在执行BGREWRITEAOF命令时,Redis服务器会维护一个AOF重写缓冲区,该缓冲区会在子进程创建新AOF文件期间,记录服务器执行的所有写命令。当子进程完成创建新AOF文件的工作之后,服务器会将重写缓冲区中的所有内容追加新AOF文件的末尾,使得新旧两个AOF文件所保存的数据库状态一致。最后,服务器用新的AOF文件替换旧的AOF文件,以此来完成AOF文件重写操作。

可以看到执行重写操作后,aof文件体积确实缩减了很多!

redis之RDB持久化与AOF持久化的更多相关文章

  1. 详解Redis RDB持久化、AOF持久化

    1.持久化 1.1 持久化简介 持久化(Persistence),持久化是将程序数据在持久状态和瞬时状态间转换的机制,即把数据(如内存中的对象)保存到可永久保存的存储设备中(如磁盘). 1.2 red ...

  2. 《面试官之你说我听》:简明的图解Redis RDB持久化、AOF持久化

    欢迎关注文章这一系列,一起学习 <提升能力,涨薪可待篇> <面试知识,工作可待篇> <实战演练,拒绝996篇> 如果此文对你有帮助.喜欢的话,那就点个赞呗,点个关注 ...

  3. Redis数据持久化—RDB持久化与AOF持久化

    目录 Redis数据持久化-RDB持久化与AOF持久化 RDB持久化 RDB文件的创建 RDB文件的载入 自动间隔性保存 检查保存条件是否满足 AOF持久化 AOF持久化的实现 AOF文件的载入与数据 ...

  4. Redis数据持久化之AOF持久化

    一.RDB持久化的缺点创建RDB文件需要将服务器所有的数据库的数据都保存起来,这是一个非常耗费资源和时间的操作,所以服务器需要隔一段时间才能创建一个新的RDB文件,就也是说创建RDB文件的操作不能执行 ...

  5. 《Redis设计与实现》- AOF持久化

    1. AOF持久化 Redis AOF 持久化是通过保存Redis服务器所执行的写命令来记录数据库状态的. 2. RDB持久化与AOF持久化的区别 RDB持久化 RDB持久化通过保存数据中的键值对来记 ...

  6. 9.快照持久化和AOF持久化

    持久化功能redis为了内部数据的安全考虑,会把本身的数据以文件形式保存到硬盘中一份,在服务器重启之后会把硬盘中的数据恢复到内存(redis)的里边. 数据保存到硬盘的过程就称为“持久化”效果. re ...

  7. Redis的两种持久化方式-快照持久化(RDB)和AOF持久化

    Redis为了内部数据的安全考虑,会把本身的数据以文件形式保存到硬盘中一份,在服务器重启之后会自动把硬盘的数据恢复到内存(redis)的里边,数据保存到硬盘的过程就称为“持久化”效果. redis有两 ...

  8. redis 笔记03 RDB 持久化、AOF持久化、事件、客户端

    RDB 持久化 1. RDB文件用于保存和还原Redis服务器所有数据库中的所有键值对数据. 2. SAVE命令由服务器进程直接执行保存操作,所以该命令会阻塞服务器. 3. BGSAVE由子进程执行保 ...

  9. redis系列:RDB持久化与AOF持久化

    前言 什么是持久化? 持久化(Persistence),即把数据(如内存中的对象)保存到可永久保存的存储设备中(如磁盘).持久化的主要应用是将内存中的对象存储在数据库中,或者存储在磁盘文件中.XML数 ...

随机推荐

  1. Spring Boot 整合 FastDFS 客户端

    原文地址:Spring Boot 整合 FastDFS 客户端 博客地址:http://www.extlight.com 一.前言 前两篇介绍整体上介绍了通过 Nginx 和 FastDFS 的整合来 ...

  2. javascript 变量定义

    一.javascript中,变量定义的位置与写在哪个<script></script>标签对内无关,只分前后顺序,写在前面的后面就能够访问,写在后面的前面会提示“未定义”. 例 ...

  3. openVPN之Luci及tap模式

    一. 1.复制luci-sc-openvpn源码到/home/tingpan/openwrt/barrier_breaker/feeds/luci/applications文件夹下. 二. /home ...

  4. Real FFT

    [文/告别年代   Email:byeyear@hotmail.com] FFT算法是针对复信号的,而现实场景中很多时候时域是实信号,此时有两种办法加快FFT的速度. 1. 使用一个N点的复FFT同时 ...

  5. 【Active入门-2】ActiveMQ学习-生产者与消费者

    1个生产者,1个消费者,使用Queue: 方式1: 生产者将消息发送到Queue中,退出: 然后运行消费者: . 可以看到,可以接收到消息. 方式2: 先运行消费者程序: 然后运行生产者: 消费者见下 ...

  6. 【Spring学习笔记-MVC-12】Spring MVC视图解析器之ResourceBundleViewResolver

    场景 当我们设计程序界面的时候,中国人希望界面是中文,而美国人希望界面是英文. 我们当然希望后台代码不需改变,系统能够通过配置文件配置,来自己觉得是显示中文界面还是英文界面. 这是,Spring mv ...

  7. spring boot学习(2) SpringBoot 项目属性配置

    第一节:项目内置属性 application.properties配置整个项目的,相当于以前的web.xml: 注意到上一节的访问HelloWorld时,项目路径也没有加:直接是http://loca ...

  8. java实验三——求平均数,数组排序(有关java保留小数位数,由于编译器版本未到1.5导致的报错format函数第二个参数不对,要求是Object[])

    package hello; import java.util.Arrays; public class 实验三更正版 { public static void main(String[] args) ...

  9. 1036 Boys vs Girls (25 分)

    1036 Boys vs Girls (25 分) This time you are asked to tell the difference between the lowest grade of ...

  10. HttpURLConnection连接超时问题

    1.问题描述 这几天测试重构后的下载框架,发现在下载过程中如果网络中断或网络较差,个别应用的下载就会阻塞卡住,一直卡在 “正在下载 xx%”.   2.问题排查和定位 思考:网络差不应该报网络异常的错 ...