Redis的强大性能很大程度是因为它所有的数据都保存在内存中。当然,如果redis重启或者服务器故障导致redis重启,内存中存放的所有Data都会丢失。但在某些情况下,我们希望Redis能够保证重启后数据不会丢失。使用redis作为nosql数据库。使用Redis作为高效的缓存服务器,缓存崩溃后对后端数据库层面的瞬时压力特别大,所有缓存同时失效可能会造成雪崩。这时候我们就希望Redis能够以某种形式将内存中的数据同步到硬盘中,这样重启后就可以根据硬盘中的记录恢复数据。Redis支持两种持久化方式,一种是RDB方式,一种是AOF(append-only-file)方式。这两种持久化方法可以单独使用,也可以结合使用。RDB:按照指定的规则“定时”将数据存储在硬盘内存中,AOF:在每次执行命令后记录命令本身。RDB模式RDB的持久化方式是通过快照来完成的,这是Redis默认的持久化方式。配置如下。#save36001#save300100#save6010000Redis允许用户自定义快照条件,当满足快照条件时,Redis会自动执行快照操作。快照的条件可以由用户在配置文件中配置。配置格式如下:save第一个参数为时间窗口,第二个为key个数,即第一个时间参数配置范围内变化的key个数大于后者的变化,满足快照条件。当条件触发时,Redis会自动在内存中生成数据的副本,并存储到磁盘上。这个过程称为“快照”。除了上述规则外,还有几种生成快照的方法。根据配置规则自动快照当用户执行SAVE或GBSAVE命令并执行FLUSHALL命令进行复制时,根据配置规则进行自动快照并修改redis.conf文件,即如果一个key在5秒内变化秒后,会生成一个rdb文件。save51#表示在3600s内至少发生一次key变化(新建、修改、删除),则重写rdb文件save300100save6010000修改文件存放路径dir/data/program/redis/binothers参数配置说明参数说明dirrdb文件默认在启动目录下(相对路径)configgetdir获取dbfilename文件名rdbcompression启用压缩可以节省存储空间,但是会消耗一些CPU计算时间。默认开启rdbchecksum使用CRC64算法进行数据校验,但是这会增加10%左右的性能消耗。如果你想获得最大的性能提升,你可以关闭这个功能。如果需要关闭RDB的持久化机制,可以参考下面的配置,开启save,注释其他规则保存""#save9001#save30010#save6010000用户执行SAVE或GBSAVE命令除了让Redis自动进行快照之外,当我们重启服务或者迁移服务器时,我们需要手动干预备份。Redis提供了两个命令来完成这个任务。保存命令如图4-24所示。当执行save命令时,Redis会同步进行一次快照操作,在快照执行过程中,所有来自客户端的请求都会被阻塞。当redis内存中数据较多时,传递这条命令会导致redis长时间没有响应。因此,不建议在生产环境中使用该命令。相反,建议使用bgsave命令。图4-24bgsave命令如图4-25所示。bgsave命令可以在后台异步执行快照操作,服务端可以持续响应来自客户端的请求。执行完BGSAVE后,Redis会立即返回ok,表示快照操作已经开始。在redis-cli终端中,可以使用如下命令获取上一次快照执行成功的时间(以UNIX时间戳格式表示)。LASTSAVE1:Redis使用fork函数复制一份当前进程(子进程)2:父进程继续接收并处理来自客户端的命令,同时子进程开始将内存中的数据写入临时文件硬盘3:当子进程写完所有数据后,会用临时文件替换旧的RDB文件。至此,一次快照操作完成。注意:redis在快照过程中不会修改rdb文件。只有在快照结束后,旧文件才会被新文件替换,这意味着RDB文件在任何时候都是完整的。这样我们就可以通过定时备份RDB文件来备份redis数据库。RDB文件是压缩后的二进制文件,比内存中的数据占用空间更小,传输更方便。bgsave异步执行快照。bgsave写入的数据是for过程中redis的数据状态。一旦fork完成,后续执行新的client命令将不会反映本次快照Redis启动后数据的变化。读取RDB快照文件,将数据从硬盘加载到内存中。根据数据的大小和服务器的性能,加载时间也不同。图4-25执行FLUSHALL命令。前面说过,这条命令会清除redis内存中的所有数据。执行这条命令后,只要redis中配置的snapshot规则不为空,即存在save规则。Redis会执行快照操作。不管规则是什么,它们都会被执行。如果没有定义快照规则,则不会执行快照操作。在进行复制(replication)时,主要以主从模式运行,redis会在复制初始化时自动进行快照。这些事会晚一些讨论;这里你只需要明白,在执行复制操作时,即使没有定义自动快照规则,也没有手动执行快照操作,它仍然会生成一个RDB快照文件。RDB数据恢复demo准备初始数据redis>setk11redis>setk22redis>setk33redis>setk44redis>setk55triggersaveredis>通过shutdown命令shutdown备份dump.rdb文件(用于后续恢复)cpdump.rdbdump.rdb.bak然后启动redis-server(systemctlrestartredis_6379),通过keys命令查看,发现数据还在keys中*模拟数据丢失,执行flushallredis>flushallshutdown(重新生成没有数据的快照,用于模拟后续数据恢复)redis>shutdown再次启动redis,通过keys命令查看,此时rdb中没有数据。恢复之前备份的rdb文件(之前保存数据的rdb快照)mvdump.rdb.bakdump.rdb再次重启redis,可以看到之前快照1保存的datakeys*文件的优缺点。优点 1.RDB是一个非常紧凑(compact)的文件,保存了redis在某个时间点的数据集,非常适合备份和容灾。 2。在生成RDB文件时,redis主进程会fork()一个子进程来处理所有的保存工作,主进程不需要进行任何磁盘IO操作。 3.RDB在恢复大数据集时比AOF更快。二、缺点1、RDB数据不能实时/秒级持久化。因为bgsave每次运行都需要fork操作创建子进程,频繁执行成本太高lost)。如果数据比较重要,想把损失降到最低,可以使用AOF的方式进行持久化。AOF方式AOF(??AppendOnlyFile):Redis默认是不开启的。AOF以日志的形式记录每一次写操作,并追加到文件中。启用后,当执行更改Redis数据的命令时,该命令会被写入AOF文件。当Redis重启时,会根据日志文件的内容从前到后执行write命令,完成数据恢复工作。AOF配置switch#switchappendonlyno/yes#filenameappendfilename"appendonly.aof"修改redis.conf重启redis后:systemctlrestartredis_6379。再次运行redis相关的操作命令,会发现在指定的dir目录下生成了appendonly.aof文件。通过vim查看文件内容如下*2$6SELECT$10*3$3set$4name$3mic*3$3set$4name$3123AOF配置相关问题的解答问题一:所有数据都是实时持久化到磁盘的吗?虽然AOF每次执行更改Redis数据库内容的操作都会将命令记录在AOF文件中,但实际上由于操作系统的缓存机制,数据并没有真正写入硬盘,而是进入系统的硬盘缓存。默认情况下,系统将每30秒执行一次同步。为了真正将硬盘缓存中的内容写入硬盘。在这30秒内,如果系统异常退出,硬盘缓存中的数据将会丢失。一般来说,启用AOF的前提是业务场景不能容忍这种数据丢失。这时候Redis需要在写入AOF文件后主动请求系统将缓存的内容同步到硬盘中。通过以下配置在redis.conf中设置同步机制。参数说明appendfsynceverysecAOF持久化策略(硬盘缓存到磁盘),默认everysec1no表示不执行fsync,操作系统保证数据同步到磁盘,最快,但不是很安全;2always表示每次写都执行fsync,保证数据同步到磁盘,效率很低;3everysec表示每秒执行一次fsync,可能会导致这1s的数据丢失。通常选择everysec,兼顾安全和效率。问题2:文件越来越大,怎么办?由于AOF持久化意味着Redis不断地将写命令记录到AOF文件中,随着Redis的不断运行,AOF文件会越来越大。文件越大,服务器内存越大,AOF恢复时间越长。例如setgupao666执行1000次,结果就是gupao=666。为了解决这个问题,Redis加入了重写机制。当AOF文件的大小超过设定的阈值时,Redis会启动AOF文件的内容压缩,只保留能够恢复数据的最小指令集。可以使用如下命令主动触发redis的重写>bgrewriteaofAOF文件重写不是重新组织原文件,而是直接读取服务器已有的key-value对,然后用一个命令替换之前记录的key-valuepairs多个命令生成一个新文件来替换原来的AOF文件。rewrite触发机制如下参数说明auto-aof-rewrite-percentage默认值为100,表示当前AOF文件大小超过上次rewrite时AOF文件大小的百分比时,将进行重写再次。如果之前没有改写过,会以启动时的AOF文件大小为准。auto-aof-rewrite-min-size默认为64M。表示限制允许重写的最小AOF文件大小。通常,当AOF文件较小时,即使有很多冗余命令,我们也不会太在意。Redis在启动时会一条一条的执行AOF文件中的命令。将硬盘中的数据加载到内存中,加载速度会比RDB慢。问题:AOF文件在重写过程中发生变化怎么办?Redis可以在AOF文件过大时在后台自动重写AOF:重写后的新AOF文件包含恢复当前数据集所需的最小命令集。改写过程如下。主进程会fork一个子进程进行AOF重写。这个改写过程并不是基于原来的aof文件,而是有点类似于快照的方式,遍历整个内存。数据,然后将它们一个一个排序成aof文件。在fork子进程的过程中,服务端仍然可以对外提供服务,那么此时重写的aof文件的数据与redis内存数据不一致怎么办?不用担心,在这个过程中,主进程的数据更新操作会缓存在aof_rewrite_buf中,也就是会开一个单独的缓存来存放rewrite时接收到的命令,缓存中的数据会在之后追加子进程重写到新的aof文件。当所有的数据都添加到新的aof文件中后,将新的aof文件重命名为正式的文件名,之后的所有操作都会写入到新的aof文件中。如果rewrite过程中出现故障,不会影响原aof文件的正常工作,只有rewrite完成后才会切换文件。因此,这个重写过程是比较靠谱的。图4-26Redis允许AOF和RDB同时开启,既保证了数据安全,又使得备份等操作变得非常容易。如果同时开启,Redis重启会使用AOF文件恢复数据,因为AOF方式的持久化可能丢失的数据较少。AOF的优缺点优点:1、AOF持久化方式提供了多种同步频率。即使使用默认的同步频率每秒同步一次,Redis最多也只会丢失1秒的数据。缺点:1.对于相同数据的Redis,AOF文件通常比RDB文件大(RDB存储的是数据快照)。2、虽然AOF提供了多种同步频率,但默认情况下,每秒同步一次的频率也有更高的性能。在高并发的情况下,RDB比AOF有更好的性能保证。