网站不备案可以上线吗,外贸网站 字体,平面设计和电子商务哪个好,网页表格代码RDB持久化
因为Redis是内存数据库#xff0c;它将自己的数据库状态储存在内存里面#xff0c;所以如果不想办法将储存在内存中的数据库状态保存到磁盘里面#xff0c;那么一旦服务器进程退出#xff0c;服务器中的数据库状态也会消失不见。
为了解决这个问题#xff0c;…RDB持久化
因为Redis是内存数据库它将自己的数据库状态储存在内存里面所以如果不想办法将储存在内存中的数据库状态保存到磁盘里面那么一旦服务器进程退出服务器中的数据库状态也会消失不见。
为了解决这个问题Redis提供了RDB持久化功能这个功能可以将Redis在内存中的数据库状态保存到磁盘里面避免数据意外丢失。
RDB持久化功能所生成的RDB文件是一个经过压缩的二进制文件通过该文件可以还原生成RDB文件时的数据库状态 RDB文件是保存在硬盘里的 如果服务器开启了AOF持久化功能那么服务器会优先使用AOF文件来还原数据库状态。 只有在AOF持久化功能处于关闭状态时服务器才会使用RDB文件来还原数据库状态。
SAVE命令会阻塞Redis服务器进程直到RDB文件创建完毕为止在服务器进程阻塞期间服务器不能处理任何命令请求
和SAVE命令直接阻塞服务器进程的做法不同BGSAVE命令会派生出一个子进程然后由子进程负责创建RDB文件服务器进程父进程继续处理命令请求
服务器在载入RDB文件期间会一直处于阻塞状态直到载入工作完成为止。
RDB文件结构
每个非空数据库在RDB文件中都可以保存为SELECTDB、db_number、key_value_pairs三个部分
SELECTDB常量的长度为1字节当读入程序遇到这个值的时候它知道接下来要读入的将是一个数据库号码。db_number保存着一个数据库号码根据号码的大小不同这个部分的长度可以是1字节、2字节或者5字节。当程序读入db_number部分之后服务器会调用SELECT命令根据读入的数据库号码进行数据库切换使得之后读入的键值对可以载入到正确的数据库中。key_value_pairs部分保存了数据库中的所有键值对数据如果键值对带有过期时间那么过期时间也会和键值对保存在一起。根据键值对的数量、类型、内容以及是否有过期时间等条件的不同key_value_pairs部分的长度也会有所不同。RDB文件中的每个key_value_pairs部分都保存了一个或以上数量的键值对如果键值对带有过期时间的话那么键值对的过期时间也会被保存在内。不带过期时间的键值对在RDB文件中由TYPE、key、value三部分组成。
AOF持久化
与RDB持久化通过保存数据库中的键值对来记录数据库状态不同AOF持久化是通过保存Redis服务器所执行的写命令来记录数据库状态的。 AOF持久化的实现: AOF持久化功能的实现可以分为命令追加append、文件写入、文件同步sync三个步骤。 当AOF持久化功能处于打开状态时服务器在执行完一个写命令之后会以协议格式将被执行的写命令追加到服务器状态的aof_buf缓冲区的末尾
为了提高文件的写入效率在现代操作系统中当用户调用write函数将一些数据写入到文件的时候操作系统通常会将写入数据暂时保存在一个内存缓冲区里面等到缓冲区的空间被填满、或者超过了指定的时限之后才真正地将缓冲区中的数据写入到磁盘里面。
但是若计算机发生停机那么保存在内存缓冲区里面的写入数据将会丢失。
为此系统提供了fsync和fdatasync两个同步函数它们可以强制让操作系统立即将缓冲区中的数据写入到硬盘里面从而确保写入数据的安全性
因为AOF文件里面包含了重建数据库状态所需的所有写命令所以服务器只要读入并重新执行一遍AOF文件里面保存的写命令就可以还原服务器关闭之前的数据库状态。
AOF重写
因为AOF持久化是通过保存被执行的写命令来记录数据库状态的AOF文件中的内容会越来越多体积过大的AOF文件很可能对Redis服务器、甚至整个宿主计算机造成影响并且AOF文件的体积越大使用AOF文件来进行数据还原所需的时间就越多。
为此Redis提供了AOF文件重写功能Redis服务器可以创建一个新的AOF文件来替代现有的AOF文件新旧两个AOF文件所保存的数据库状态相同但新AOF文件不会包含任何浪费空间的冗余命令所以新AOF文件的体积通常会比旧AOF文件的体积要小得多。
但实际上AOF文件重写并不需要对现有的AOF文件进行任何读取、分析或者写入操作而是通过读取服务器当前的数据库状态来实现的。
首先从数据库中读取键现在的值然后用一条命令去记录键值对代替之前记录这个键值对的多条命令这就是AOF重写功能的实现原理。
在实际中为了避免在执行命令时造成客户端输入缓冲区溢出重写程序在处理列表、哈希表、集合、有序集合这四种可能会带有多个元素的键时会先检查键所包含的元素数量如果元素的数量超过了redis.h/REDIS_AOF_REWRITE_ITEMS_PER_CMD常量的值那么重写程序将使用多条命令来记录键的值而不单单使用一条命令。
作为一种辅佐性的维护手段Redis不希望AOF重写造成服务器无法处理请求所以Redis决定将AOF重写程序放到子进程里执行这样做可以同时达到两个目的 子进程进行AOF重写期间服务器进程父进程可以继续处理命令请求。 子进程带有服务器进程的数据副本使用子进程而不是线程可以在避免使用锁的情况下保证数据的安全性。
不过使用子进程也有一个问题需要解决因为子进程在进行AOF重写期间服务器进程还需要继续处理命令请求而新的命令可能会对现有的数据库状态进行修改从而使得服务器当前的数据库状态和重写后的AOF文件所保存的数据库状态不一致。
为了解决这种数据不一致问题Redis服务器设置了一个AOF重写缓冲区这个缓冲区在服务器创建子进程之后开始使用当Redis服务器执行完一个写命令之后它会同时将这个写命令发送给AOF缓冲区和AOF重写缓冲区
当子进程完成AOF重写工作之后它会向父进程发送一个信号父进程在接到该信号之后会调用一个信号处理函数并执行以下工作 将AOF重写缓冲区中的所有内容写入到新AOF文件中这时新AOF文件所保存的数据库状态将和服务器当前的数据库状态一致。 对新的AOF文件进行改名原子地atomic覆盖现有的AOF文件完成新旧两个AOF文件的替换。
在整个AOF后台重写过程中只有信号处理函数执行时会对服务器进程父进程造成阻塞在其他时候AOF后台重写都不会阻塞父进程这将AOF重写对服务器性能造成的影响降到了最低。