08Redis持久化

本篇文章介绍Redis持久化的技术说明。

官网文档:https://redis.io/topics/persistence

 

一.Redis中提供的不同持久化选项

  • RDB(Redis DataBase):RDB 持久性以指定的时间间隔执行数据集的时间点快照。
  • AOF(Append Only File):AOF 持久化记录服务器收到的每个写操作,在服务器启动时会再次播放,重建原始数据集。命令使用与 Redis 协议本身相同的格式以仅附加的方式记录。当日志变得太大时,Redis 能够在后台重写日志。
  • 无持久性:如果您希望数据在服务器运行时一直存在,您可以完全禁用持久性。
  • RDB + AOF:可以在同一个实例中组合 AOF 和 RDB。请注意,在这种情况下,当 Redis 重新启动时,AOF 文件将用于重建原始数据集,因为它保证是最完整的。

 

二.持久化是怎么执行的

Redis会单独创建(fork)一个子进程来进行持久化,会先将数据写入一个临时文件中,待持久化过程都结束了,再用这个临时文件替换上次持久化好的文件。整个过程中,主进程是不进行任何IO操作的,这就确保了极高的性能,如果需要进行大规模数据的恢复,且对于数据恢复的完整性不是非常敏感,那RDB方式要比AOF方式更加高效。RDB的缺点是最后一次持久化后的数据可能丢失

Fork的作用是赋值一个与当前进程一样的进程。新进程中的所有数据(变量,环境变量,程序计数器等)数值和原进程一致,但是是一个全新的进程,并作为原进程的子进程。

在Linux程序中,fork会产生一个和父进程完全相同的子进程,但子进程在此后会exec系统调用,出于效率考虑,Linux中引入了'写时复制技术'。

一般情况父进程和子进程会共享共同一段物理内存,只有进程空间的各段内容要发生变化时,才会将父进程的内容复制一份给子进程。

 

 

三.RDB配置文件中的参数设置

在Redis中的redis.conf文件中包含了RDB的相关配置。

 1 ################################ SNAPSHOTTING  ################################
 2 
 3 # Save the DB to disk. //将数据库保存到磁盘
 4 #
 5 # save <seconds> <changes>
 6 #
 7 # Redis will save the DB if both the given number of seconds and the given //如果达到给定的毫秒数和给定的写操作的次数,Redis就会保存数据库
 8 # number of write operations against the DB occurred.
 9 #
10 # Snapshotting can be completely disabled with a single empty string argument //使用一个空字符串参数可以完全禁用快照
11 # as in following example:
12 #
13 # save ""
14 #
15 # Unless specified otherwise, by default Redis will save the DB:   //除非另有规定,默认情况下Redis将保存数据库
16 #   * After 3600 seconds (an hour) if at least 1 key changed        //3600秒(一小时)后,如果至少有一个Key发生了变化
17 #   * After 300 seconds (5 minutes) if at least 100 keys changed    //300秒(5分钟)后,如果至少更改了100个键
18 #   * After 60 seconds if at least 10000 keys changed                //60秒后,如果至少10000个键发生了变化
19 #
20 # You can set these explicitly by uncommenting the three following lines. //您可以通过取消以下三行的注释来显式地设置它们
21 #
22 # save 3600 1
23 # save 300 100
24 # save 60 10000
25 
26 # By default Redis will stop accepting writes if RDB snapshots are enabled  //默认情况下,如果启用RDB快照,Redis将停止接受写操作(至少一个保存点)和最新的后台保存失败。
27 # (at least one save point) and the latest background save failed.
28 # This will make the user aware (in a hard way) that data is not persisting  //这将使用户意识到(以一种强硬的方式)数据没有正确地保存在磁盘上,否则很可能没有人会注意到,并且会发生一些灾难。
29 # on disk properly, otherwise chances are that no one will notice and some
30 # disaster will happen.
31 #
32 # If the background saving process will start working again Redis will    //如果后台保存过程重新开始工作,Redis将自动再次允许写操作。
33 # automatically allow writes again.
34 #
35 # However if you have setup your proper monitoring of the Redis server     //但是,如果您已经设置了对Redis服务器和持久性的正确监视,
36 # and persistence, you may want to disable this feature so that Redis will  //那么您可能需要禁用此功能,以便即使在磁盘、权限等方面出现问题时,Redis仍能正常工作。
37 # continue to work as usual even if there are problems with disk,
38 # permissions, and so forth.
39 stop-writes-on-bgsave-error yes
40 
41 # Compress string objects using LZF when dump .rdb databases?  //在转储.rdb数据库时使用LZF压缩字符串对象?
42 # By default compression is enabled as it's almost always a win. //默认情况下,压缩是启用的,因为它几乎总是成功的。
43 # If you want to save some CPU in the saving child set it to 'no' but //如果要在保存子级中保存一些CPU,请将其设置为“否”,但如果有可压缩的值或键,则数据集可能会更大。
44 # the dataset will likely be bigger if you have compressible values or keys.
45 rdbcompression yes
46 
47 # Since version 5 of RDB a CRC64 checksum is placed at the end of the file. //自从RDB版本5,CRC64校验和放在文件的末尾。
48 # This makes the format more resistant to corruption but there is a performance  //这使格式更能抵抗损坏,但在保存和加载RDB文件时,性能会受到影响(约10%),因此可以禁用它以获得最大性能。
49 # hit to pay (around 10%) when saving and loading RDB files, so you can disable it
50 # for maximum performances.
51 #
52 # RDB files created with checksum disabled have a checksum of zero that will  //在禁用校验和的情况下创建的RDB文件的校验和为零,这将告诉加载代码跳过检查。
53 # tell the loading code to skip the check.
54 rdbchecksum yes
55 
56 # Enables or disables full sanitation checks for ziplist and listpack etc when   //在加载RDB或还原负载时启用或禁用ziplist和listpack等的完全卫生检查
57 # loading an RDB or RESTORE payload. This reduces the chances of a assertion or  //这减少了以后处理命令时断言或崩溃的机会。
58 # crash later on while processing commands.
59 # Options:
60 #   no         - Never perform full sanitation  //切勿进行全面卫生
61 #   yes        - Always perform full sanitation  //始终保持全面卫生
62 #   clients    - Perform full sanitation only for user connections.
63 #                Excludes: RDB files, RESTORE commands received from the master
64 #                connection, and client connections which have the
65 #                skip-sanitize-payload ACL flag.
66 # The default should be 'clients' but since it currently affects cluster  //默认值应该是'clients',但是由于它当前通过MIGRATE影响集群的重编,所以默认情况下它被临时设置为'no'。
67 # resharding via MIGRATE, it is temporarily set to 'no' by default.
68 #
69 # sanitize-dump-payload no  //清理转储负载
70 
71 # The filename where to dump the DB  //将数据库转储到的文件名
72 dbfilename "dump.rdb"
73 
74 # Remove RDB files used by replication in instances without persistence  //在未启用持久性的实例中删除复制使用的RDB文件。
75 # enabled. By default this option is disabled, however there are environments  //默认情况下,此选项处于禁用状态,但是在某些环境中,出于管理法规或其他安全考虑,
76 # where for regulations or other security concerns, RDB files persisted on     //应尽快删除由主服务器保留在磁盘上以馈送副本的RDB文件,或由副本存储在磁盘上以加载这些文件以进行初始同步
77 # disk by masters in order to feed replicas, or stored on disk by replicas
78 # in order to load them for the initial synchronization, should be deleted
79 # ASAP. Note that this option ONLY WORKS in instances that have both AOF        //请注意,此选项仅适用于同时禁用AOF和RDB持久性的实例,否则将完全忽略。
80 # and RDB persistence disabled, otherwise is completely ignored.
81 #
82 # An alternative (and sometimes better) way to obtain the same effect is     //获得相同效果的另一种方法(有时更好)是在主实例和副本实例上使用无盘复制。
83 # to use diskless replication on both master and replicas instances. However  //但是,对于副本,无磁盘并不总是一种选择。
84 # in the case of replicas, diskless is not always an option.
85 rdb-del-sync-files no
86 
87 # The working directory.
88 #
89 # The DB will be written inside this directory, with the filename specified   //DB将被写入这个目录,使用上面使用'dbfilename'配置指令指定的文件名。
90 # above using the 'dbfilename' configuration directive.
91 #
92 # The Append Only File will also be created inside this directory.   //只附加的文件也将在这个目录中创建。
93 #
94 # Note that you must specify a directory here, not a file name.  //请注意,必须在此处指定目录,而不是文件名。
95 dir "/usr/local/redis-6.2.4/bin"

 

四.RDB的备份和恢复

测试步骤:

  1. 将redis.conf里面的
    save 3600 1      #开启
    save 300 100     #开启,并将该值设置为 save 30 10,意思是30秒内有10Key发生变化就进行RDB写操作
    save 60 10000    #开启

     

     

  2. 保存该配置文件的修改并退出
  3. 重新启动redis。并查看该初始dump.rdb文件的大小

  4. 进入redis-cli并在30秒内put 12条数据

    

   5.查看dump.rdb文件的大小

    

   6.将dump.rdb备份

    

   7.关闭redis-server,并将dump.rdb删除(相当于redis-server出现故障,我们用备份文件dump.rdb.bak进行恢复)

   8.将dump.rdb.bak修改为dump.rdb,并启动redis-server,并查看数据

    

   9.发现dump.rdb中只持久化了10个数据。这是因为在30秒有10个key发生了变化。那么根据配置文件中的配置,就会将这10个Key进行持久化。当第11个key set进入后,就会从当前key重新计时30s,但是在set k11 k12 的时候我们并不满足在30s内变化了10个key,因此这两个并没有被持久化即没有被写进dump.rdb文件中。因此,当我们使用该dump.rdb对redis-server进行启动的时候,并没有k11 和k12。

 

 五.RDB的优势劣势

优势:

  • 适合大规模的数恢复
  • 数据完整性和一致性要求不高的场景更加适用
  • 节省磁盘空间
  • 恢复速度快

劣势:

  • Fork的时候,内存中的数据被克隆了一份,大致2倍的膨胀性需要考虑
  • 虽然Redis在fork的时候使用写时拷贝技术,但是如果数据庞大时还是比较消耗性能
  • 在备份周期在一定间隔时间做一次备份,所以如果redis意外down掉的话,就会丢失最后一次快照后修改的数据。

 

posted @ 2021-07-23 00:17  Costin  阅读(94)  评论(0)    收藏  举报