持久化存储是将 Redis 存储在内存中的数据存储在硬盘中,实现数据的永久保存。
我们都知道 Redis 是一个基于内存的 nosql 数据库,内存存储很随意马虎造成数据的丢失,由于当做事器关机等一些非常情形都会导致存储在内存中的数据丢失。

持久化存储分类

在 Redis 中,持久化存储分为两种。
一种是 aof 日志追加的办法,其余一种是 rdb 数据快照的办法。

phpredis缓存周期Redis持久化存储详解一 NoSQL

RDB持久化存储

什么是RDB持久化存储

RDB持久化存储即是将redis存在内存中的数据以快照的形式保存在本地磁盘中。

.RDB持久化存储分为自动备份和手动备份

1.手动备份通过 save 命令和 bgsave 命令。
save是同步壅塞,而 bgsave 是非壅塞(壅塞实际发生在 fork 的子进程中)。
因此,在我们实际过程中大多是利用bgsave命令实现备份.

redis> SAVEOKredis> BGSAVEBackground saving started

2.自动备份

a.修正配置项 save m n即表示在 m 秒内实行了 n 次命令则进行备份.

b.当Redis 从做事器项主理事器发送复制要求时,主理事器则会利用 bgsave命令天生 rbd 文件,然后传输给从做事器.

c.当实行 debug reload 命令时也会利用 save 命令天生rdb文件.

d.当利用 shutdown 命令关掉做事时,如果没有启用 aof办法实现持久化则会采取bgsave的办法做持久化.同时shutdown后面可以加备份参数[nosave|save].

bgsave持久化存储实现事理

1.实行bgsave命令,Redis父进程判断当前是否存在正在实行的子进程,如果存在则直接返回.

2.父进程fork一个子进程(fork的过程中会造成壅塞的情形),这个过程可以利用info stats命令查看latest_fork_usec选项,查看最近一次fork操作小号的韶光,单位是奇妙.

3.父进程fork完之后,则会返回Background saving started信息提示,此时fork壅塞解除.

4.fork出的子进程开始根据父进程内存数据天生临时的快照文件,然后更换原文件.利用lastsave命令可以查看末了一次天生rdb的韶光,对应info的rdb_last_save_time选项.

5.当备份完毕之后向父进程发送完成信息,详细可以见info Persistence下的rbd_选项.

RDB持久化的上风与劣势

上风:

1.文件实现的数据快照,全量备份,便于数据的传输.比如我们须要把A做事器上的备份文件传输到B做事器上面,直接将rdb文件拷贝即可.

2.文件采取压缩的二进制文件,当重启做事时加载数据文件,比aof办法更快.

劣势:

1.rbd采取加密的二进制格式存储文件,由于Redis各个版本之间的兼容性问题也导致rdb由版本兼容问题导致无法再其他的Redis版本中利用.

2.时效性差,随意马虎造成数据的不完全性.由于rdb并不是实时备份,当某个韶光段Redis做事涌现非常,内存数据丢失,这段韶光的数据是无法规复的,因此易导致数据的丢失.

RDB文件常见的处理办法

1.当碰着磁盘写满情形,可以利用如下命令来切换存储磁盘

// dirName则是新的存储目录名(该办法同样适用于aof格式)config set dir dirName

2.文件压缩处理,虽然对CPU具有花费,但是减少体积的暂用,同时做文件传输(主从复制)也减少花费.

// 修正压缩开启或关闭config set rdbcompression yes|no

3.rbd备份文件破坏检测.可以利用redis-check-rdb工具检测rdb文件,该工具默认在/usr/local/bin/目录下面.

[root@syncd redis-data]# /usr/local/bin/redis-check-rdb ./6379-rdb.rdb [offset 0] Checking RDB file ./6379-rdb.rdb[offset 26] AUX FIELD redis-ver = '5.0.3'[offset 40] AUX FIELD redis-bits = '64'[offset 52] AUX FIELD ctime = '1552061947'[offset 67] AUX FIELD used-mem = '852984'[offset 83] AUX FIELD aof-preamble = '0'[offset 85] Selecting DB ID 0[offset 105] Checksum OK[offset 105] \o/ RDB looks OK! \o/[info] 1 keys read[info] 0 expires[info] 0 already expired

AOF持久化存储

AOF持久化存储是什么

AOF持久化存储便是以日志的形式将redis存储在aof_buf缓冲区中的数据写入到磁盘中。
简而言之,便是记录redis的操作日志,将redis实行过的命令记录下载,当我们须要数据规复时,redis去重新实行一越日记文件中的命令.

如何配置持久化存储// 将no改为yes,掌握aof开启与否appendonly no// 掌握aof文件名称,存储的目录便是dir配置项appendfilename \"大众appendonly.aof\"大众// 三种备份策略(三者只须要开启以一个即可)# appendfsync always // 命令写入立即写入磁盘appendfsync everysec // 每秒实现文件的同步,写入磁盘# appendfsync no // 随机进行文件的同步,同步操作则交给操作系统来卖力,常日韶光是最长30sAOF持久化存储实现事理

aof日志追加办法实现持久化存储,须要经历如下四个过程.命令写入->文件同步->文件重写->文件重载

1.redis命令写入,此时会将redis命令写入aof_buf换从区.

2.缓冲区中数据根据备份策略实现写入日志文件.

3.当aof的文件越来越弘大,会根据我们的配置策略来实现aof的重写,实现文件的压缩,减少体积.

4.当redis重新启动时,在去重写加载aof文件,达到数据规复的目的.

命令写入

命令写入紧张是将文件实行过的命令写入到日志文件中.并且日志文件尊徐文本协议格式,下面示例代码便是aof日志文件中存储的内容格式.

3\r\n$3\r\nset\r\n$5\r\nhello\r\n$5\r\nworld\r\n

aof采取的是文本协议格式。
紧张是缘故原由根据资料提示,可以能使由于如下缘故原由.

1.文本协议的兼容性好.前面我们提及到了rdb文件是进行二进制加密,可能不同版本之间会涌现不兼容的情形,采取文本协议可以加避免该问题。
同时文本协议也可以减少跨平台利用所带来的诸多问题.

2.可读性强.由于aof是将命令写入文件中,我们可以直接查看命令内容,同时也可以修正日志文件内容.

3.开启aof后,所有的文件文件都包含追加操作,直接采取文本协议,减少二次开销(这一点,个人不是很理解.由于我们的aof是保存的是命令,当我们再次去加载的时候,会去实行一次里面的命令,当文件大的时候该当是比较耗时的吧。
如果没有做好文件重写策略,大量重复无效的命令实行,对付二进制加密的rdb格式,不须要再去转换,这一点确实可以减少二次开销).

文件写入

文件写入是将aof_buf缓冲区的命令写入到文件中.文件写入的策略有如下三种办法

配置项 配置解释 always 命令写入到aof_buf缓冲区中之后立即调用系统的fsync操作同步到aof文件中,fsync完成后线程返回. everysec 命令写入到aof_buf缓冲区后每隔一秒调用系统的write操作,write完成后线程返回. no 命令写入aof_bug缓冲区后调用系统write操作,不对aof文件做fsync同步,同步硬盘操作由系统操作完成,韶光一样平常最长为30s.

系统调用write和fsync解释:

·write操作会触发延迟写( delayed write) 机制。
Linux在内核供应页缓冲区用来提高硬盘IO性能。
write操作在写入系统缓冲区后直接返回。
同步硬盘操作依赖于系统调度机制, 例如: 缓冲区页空间写满或达到特定时间周期。
同步文件之前, 如果此时系统故障宕机, 缓冲区内数据将丢失.

·fsync针对单个文件操作( 比如AOF文件) , 做逼迫硬盘同步, fsync将壅塞直到写入硬盘完成后返回, 担保了数据持久化.

文件写入策略剖析

配置为always时, 每次写入都要同步AOF文件, 在一样平常的SATA硬盘上, Redis只能支持大约几百TPS写入, 显然跟Redis高性能特性背道而驰,

不建议配置.

配置为no。
由于操作系统每次同步AOF文件的周期不可控, 而且会加大每次同步硬盘的数据量, 虽然提升了性能, 但数据安全性无法担保.

配置为everysec。
是建议的同步策略, 也是默认配置, 做到兼顾性能和数据安全性。
理论上只有在系统溘然宕机的情形下丢失1秒的数据.

文件重载

1.为什么要文件做文件重载操作?

由于aof采取的这天记追加,我们redis命令不断的写入,aof文件的体积也也会不断的增加.因此redis引入了aof重写机制达到减小aof文件体积.aof文件重写是把redis进程内的数据转换为写命令同步到新的aof文件的过程(这一点实在不是特殊明白,文件重写不是针对aof文件文件做操作的吗?为什么这里是将redis进程内的数据转换为命令写入文件,这里的进程内的数据不是太明白,还有待深入研究.个人理解的便是将旧的aof文件内容根据重写策略,进行优化天生新的aof文件。
).

2.文件重载有什么好处?

文件重载紧张优化的地方有如下三点。
利用文件重载既可以减少文件的体积,同时去掉了一些无效的操作,可以加快文件重载效率.

a.将一些在进程内无效的数据不在写入新的文件.如过期的键.

b.去掉一些无效的命令.如del key1.

c.简化操作.如lpush list a,lpush list b.直接可以简化为lpush list a b.

3.文件重载由那些办法?

文件重载有自动触发机制和手动触发机制.

手动触发机制:直策应用bgrewriteaof命令即可.该命令在fork子进程的时候会发生壅塞.

自动触发机制:

auto-aof-rewrite-min-size:aof重写时文件最小的体积,默认的是64M.

auto-aof-rewrite-percentage:代表当前AOF文件空间( aof_current_size) 和上一次重写后AOF文件空间( aof_base_size) 的比值.

自动触发机遇=aof_current_size>auto-aof-rewrite-minsize&&( aof_current_size-aof_base_size) /aof_base_size>=auto-aof-rewritepercentage

个中aof_current_size和aof_base_size可以在info Persistence统计信息中查看.

4.文件重载实现的事理是若何的?

1.实行重写命令,判断是否存在子进程。

如果已经有子进程在进行aof重写,则会提示如下信息.

ERR Background append only file rewriting already in progress

如果已经存在子进程在进行bgsave操作,重写命令会延迟到bgsave命令完成之后进行,会返回如下信息.

Background append only file rewriting scheduled

2.父进程会fork一个子进程,在fork子进程的过程中会造成壅塞.

3.fork子进程结束壅塞解除,进行其他新的命令操作.新的命令依旧根据文件写入策略同步数据,担保aof机制精确进行(图中3.1).

4.子进程在进行写的过程中,由于fork操作利用的是写时复制技能,子进程只能共享fork操作时内存保留的数据,新的数据是无法操作的.父进程在这过程中仍旧在相应其他的命令,于是Redis会利用aof重写缓存区来保存这部分新的数据(图中3.2).

5.子进程进行根据重写规则将数据写入到新的aof文件中,并且每次写入有大小限定,通过aof-rewrite-incremental-fsync配置项来掌握,默认是32M,这样可以见减少单次刷盘(I/O写)造成硬盘壅塞.

6.子进程在完成重写之后,会向父进程发送信息,父进程更新统计信息.可参看info persistence下的aof_干系统计。

7.父进程会把新写入存在aof重写缓冲区的数据写入到aof文件中(图5.2).

8.将新的aof文件更换掉旧的aof文件.

在第3和4中,实在不是特殊理解.不理解的是为什么父进程在相应新的命令会写入旧的aof文件,还要aof重写缓存区.个人理解的是,父进程在进行新命令写入处理的策略是,按照正常的备份策略写入旧的aof的同时也把新的命令写入重写缓冲区,在第5.2中将这部分新的数据写入到新的aof文件中,这样担保数据的完全性.

文件重载

文件重载便是将文件重新加入到redis做事中.比如redis做事重启用于数据规复.redis的重载机制非常完善,详细流程如下.

AOF文件常见的问题处理

1.文件破坏

我们在加载破坏的文件是可能提示如下信息.

Bad file format reading the append only file: make a backup of your AOF file,then use ./redis-check-aof --fix <filename>

此时我们可以利用redis-check-aof --fix命令进行修复(记得对文件做个备份).修复后利用diff-u进行数据比拟,找出部分丢失的数据.

2.文件加载不完全

这可能是数据在备份的时候,redis做事非常,导致备份不完全.可以利用redis的aof-load-truncated兼容该非常

AOF的优缺陷

优点:

多种文件写入(fsync)策略.

数据实时保存,数据完全性强.纵然丢失某些数据,制订好策略最多也是一秒内的数据丢失.

可读性强,由于利用的是文本协议格式来存储的数据,可有直接查看操作的命令,同时也可以手动改写命令.

缺陷:

文件体积过大,加载速率比rbd慢.由于aof记录的是redis操作的日志,一些无效的,可简化的操作也会被记录下来,造成aof文件过大.但该办法可以通过文件重写策略进行优化.

选择AOF还是RDB进行数据的持久化

1.针对不同的情形来选择,建议利用两种办法相结合.

2.针对数据安全性、完全性哀求高的采取aof办法.

3.针对不太主要的数据可以利用rdb办法.

4.对付数据进行全量备份,便于数据备份的可以采取rdb办法.

原文转自微信"大众年夜众号:浪子编程走四方

作者:士兵7

链接:https://www.imooc.com/article/282814

来源:慕课网

本文原创发布于慕课网 ,转载请注明出处,感激互助