Redis持久化机制(文末有福利)

Stella981
• 阅读 620

        上一篇主要针对Redis的内存淘汰机制以及Redis容易引发的三大问题:缓存击穿、缓存穿透以及缓存雪崩进行了详细的讲解以及提供了业界常用的解决方案。本篇主要讲讲Redis的持久化机制,Redis受开发者欢迎的一大原因就是因为可持久化的特性。我们如何保证Redis宕机之后重启可以将数据进行恢复?所以一般情况下我们需要定时进行持久化将内存中的数据写入到硬盘中。而Redis中支持两种不同的持久化机制:RDB持久化以及AOF持久化。

Redis持久化机制(文末有福利)

         快照持久化是一次全量备份,备份的是内存数据的二进制序列化格式。而AOF持久化是增量备份,记录的是内存数据修改的指令记录文本。所以AOF持久化生成的日志会随着运行时间变长而变得越来越臃肿,每次重启Redis都需要加载AOF日志进行指令重放,所以需要定期重写AOF日志进行瘦身操作。

快照持久化(RDB)

RDB 持久化是指在指定的时间间隔内将内存中的数据集快照写入磁盘,实际操作过程是fork一个子进程,子进程负责将数据集写入临时文件由于os的写时复制机制父子进程会共享相同的物理界面,当父进程处理写请求时os会为父进程创建页面副本,所以紫禁城地址空间的数据实际上就是一个快照,写入成功后,再替换之前的文件,用二进制压缩存储。RDBRedis默认的持久化方式,会在对应的目录下生产一个dump.rdb文件,重启会通过加载dump.rdb文件恢复数据。Redis使用操作系统的多进程COW机制实现RDB持久化。

优点:

  • 只有一个备份文件dump.rdb,方便持久化备份;

  • 容灾性好,一个文件可以保存到其他存储介质;

  • 性能最大化,fork出子进程来完成写操作,让主进程继续处理命令,所以是IO最大化(使用单独子进程来进行持久化,主进程不会进行任何IO操作,保证了redis的高性能) ;

  • 如果数据集偏大,RDB的启动效率会比AOF更高。

缺点****:

  • 数据安全性低。

  • 如果当数据集较大时,可能会导致整个服务器停止服务。

RDB 持久化是 Redis 默认采用的持久化方式,可以在 redis.conf 配置文件中进行配置RedisN秒内如果超过Mkey被修改就自动做快照:

  • save 900 1 :在15分钟内,如果至少有1key发生变化,Redis就会自动触发BGSAVE命令创建快照。

  • save 300 10 :在5分钟内,如果至少有10key发生变化,Redis就会自动触发BGSAVE命令创建快照。

  • save 60 10000 :在1分钟之后,如果至少有10000key发生变化,Redis就会自动触发BGSAVE命令创建快照。

AOF持久化

AOF持久化是以日志的形式记录每一个增删操作,会将所有增删操作通过write函数追加到文件中。AOF的出现是为了弥补RDB的不足(数据的不一致性),所以它采用日志的形式来记录每个写操作,并追加到文件中。Redis 重启会通过执行文件中保存的写命令在内存中重建整个数据库的内容。与快照持久化相比,AOF 持久化的实时性更好,因此已成为主流的持久化方案。 默认情况下 Redis 没有开启 AOF持久化,可以通过设置 appendonly 参数开启:

appendonly yes

Redis通过fork出子进程,子进程根据内存中的快照,往临时文件中写入重建数据库状态的指令,父进程继续处理请求,当子进程将快照内容写入到临时文件中则发信号通知父进程将缓存中的写操作也写入到临时文件中,最后使用临时文件替代旧备份文件并进行重命名。AOF 文件的保存位置和 RDB 文件的位置相同,都是通过 dir 参数设置的,默认的文件名是 appendonly.aof。

在 Redis 的配置文件中存在三种不同的 AOF 持久化方式,它们分别是:

  • appendfsync always :每次有数据修改发生时都会写入AOF文件

  • appendfsync everysec :每秒钟同步一次,将多个写命令同步到硬盘

  • appendfsync no :让操作系统决定何时进行同步

用户可以使用appendfsync everysec选项 ,让 Redis 每秒同步一次 AOF 文件,这样Redis性能几乎不会受到影响,而且这样即使出现宕机,用户最多只会丢失一秒之内产生的数据。当硬盘忙于执行写入操作的时候,Redis 还会优雅的放慢自己的速度以便适应硬盘的最大写入速度。

优点:

  • 数据安全性更高,AOF持久化可以配置appendfsyn****c属性

  • 通过append模式写文件,即使中途服务器宕机,可以通过redis-check-aof工具解决数据一致性问题。

  • AOF机制的rewrite模式。

缺点:

  • AOF文件比RDB文件大,且恢复速度慢;

  • 数据集大的时候,比RDB启动效率低。

  • 根据同步策略的不同,AOF在运行效率上往往会慢于RDB

对于Redis的两种持久化机制的选择,主要还是得针对特定的系统讨论,看是可以牺牲一定的性能使用AOF持久化换取缓存一致性,还是在增删操作频繁时关闭备份,等到Redis空闲手动saveRDB持久化备份。 所以其实最佳方案应该是采用混合持久化方案,开启混合持久化后,AOF重写日志时会将RDB持久化的内容写到AOF文件开头,于是在Redis重启时,可以先加载RDB的内容,再对增量的AOF日志进行重放,提升Redis重启的效率。

欢迎关注公众号: 程序猿周先森。

Redis持久化机制(文末有福利)

每日阅读一篇文章,小程序扫码签到打卡。本周阅读次数超过四天则有机会获得JavaScript DOM编程艺术 、Java虚拟机规范或者深入理解ES6书籍一本。打卡计划获奖者必须为公众号关注者,开奖时中奖者公众号关注时间必须大于48小时。参与者从公众号菜单进入交流群,每天早晨发布当天签到二维码到交流群中。

Redis持久化机制(文末有福利)

推荐阅读

Redis优雅实现分布式锁**
**

Redis与数据库数据一致性

Redis缓存击穿、缓存穿透、缓存雪崩

本文分享自微信公众号 - 程序猿周先森(zhanyue_org)。
如有侵权,请联系 support@oschina.cn 删除。
本文参与“OSC源创计划”,欢迎正在阅读的你也加入,一起分享。

点赞
收藏
评论区
推荐文章
blmius blmius
3年前
MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1
文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s
皕杰报表之UUID
​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为
待兔 待兔
5个月前
手写Java HashMap源码
HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程22
Jacquelyn38 Jacquelyn38
3年前
2020年前端实用代码段,为你的工作保驾护航
有空的时候,自己总结了几个代码段,在开发中也经常使用,谢谢。1、使用解构获取json数据let jsonData  id: 1,status: "OK",data: 'a', 'b';let  id, status, data: number   jsonData;console.log(id, status, number )
Stella981 Stella981
3年前
KVM调整cpu和内存
一.修改kvm虚拟机的配置1、virsheditcentos7找到“memory”和“vcpu”标签,将<namecentos7</name<uuid2220a6d1a36a4fbb8523e078b3dfe795</uuid
Stella981 Stella981
3年前
Nginx + lua +[memcached,redis]
精品案例1、Nginxluamemcached,redis实现网站灰度发布2、分库分表/基于Leaf组件实现的全球唯一ID(非UUID)3、Redis独立数据监控,实现订单超时操作/MQ死信操作SelectPollEpollReactor模型4、分布式任务调试Quartz应用
Easter79 Easter79
3年前
Twitter的分布式自增ID算法snowflake (Java版)
概述分布式系统中,有一些需要使用全局唯一ID的场景,这种时候为了防止ID冲突可以使用36位的UUID,但是UUID有一些缺点,首先他相对比较长,另外UUID一般是无序的。有些时候我们希望能使用一种简单一些的ID,并且希望ID能够按照时间有序生成。而twitter的snowflake解决了这种需求,最初Twitter把存储系统从MySQL迁移
Wesley13 Wesley13
3年前
mysql设置时区
mysql设置时区mysql\_query("SETtime\_zone'8:00'")ordie('时区设置失败,请联系管理员!');中国在东8区所以加8方法二:selectcount(user\_id)asdevice,CONVERT\_TZ(FROM\_UNIXTIME(reg\_time),'08:00','0
Wesley13 Wesley13
3年前
MySQL部分从库上面因为大量的临时表tmp_table造成慢查询
背景描述Time:20190124T00:08:14.70572408:00User@Host:@Id:Schema:sentrymetaLast_errno:0Killed:0Query_time:0.315758Lock_
Python进阶者 Python进阶者
11个月前
Excel中这日期老是出来00:00:00,怎么用Pandas把这个去除
大家好,我是皮皮。一、前言前几天在Python白银交流群【上海新年人】问了一个Pandas数据筛选的问题。问题如下:这日期老是出来00:00:00,怎么把这个去除。二、实现过程后来【论草莓如何成为冻干莓】给了一个思路和代码如下:pd.toexcel之前把这