您的位置:首页 > 科技 > IT业 > redis的持久化

redis的持久化

2024/12/23 11:58:58 来源:https://blog.csdn.net/weixin_69039908/article/details/140345915  浏览:    关键词:redis的持久化
        Redis是⼀个基于内存的数据库,它的数据是存放在内存中,内存有个问题就是关闭服务或者断电会丢失。Redis的数据也⽀持写到硬盘中,这个过程就叫做持久化。
Redis提供如下2中持久化⽅式:
RDB Redis DataBase :在指定的时间间隔内,定时的将 redis 存储的数据⽣成 Snapshot 快照并存储到磁盘等介质上;
AOF Append Of File :将 redis 执⾏过的所有写指令记录下来,在下次 redis 重新启动时,只要把这些写指令从前到后再重复执⾏⼀遍,就可以实现数据恢复了。

AOF+RDB RDB AOF 两种⽅式也可以同时使⽤,在这种情况下,如果 redis 重启的话,则会优先采⽤ AOF ⽅式来进⾏数据恢复,这是因为 AOF ⽅式的数据恢复完整度更⾼。

1.RDB 

        Redis Database Backup file(Redis数据备份⽂件 ) ,也被叫作 Redis 数据快照。简单的来说就是把内存中的所有数据都记录到磁盘中。当 Redis 实例故障重启后,从磁
盘读取快照⽂件(⼆进制⽂件),恢复数据。快照⽂件称为 RDB ⽂件。
我们知道 Redis 是单线程程序,这个线程要 同时负责多个客户端套接字的并发读写操作和内存数据结构的逻辑读写
        在服务线上请求的同时,Redis 还需要进⾏内存快照,内存快照要求 Redis 必须进⾏⽂件 IO 操作,这意味着单线程同时在服务线上的请求还要进⾏⽂件 IO 操作,⽂件 IO
操作会严重拖垮服务器请求的性能。还有个重要的问题是为了不阻塞线上的业务,就需要边持久化边响应客户端请求。

SAVE的执⾏时机:

1. 执⾏ save 命令
2. 执⾏ bgsave 命令
3. 触发 RDB 条件时候
save 900 1
900 秒内,如果⾄少有 1 key 被修改,则执⾏ bgsave , 如果是 save "" 则表示
禁⽤ RDB

bgsave

        Redis 在持久化时会调⽤ glibc 的函数 fork 产⽣⼀个⼦进程,快照持久化完全交给⼦进程来处理,⽗进程继续处理客户端请求。⼦进程刚刚产⽣时,它和⽗进程共享内存⾥⾯的代码段和数据段。这时你可以将⽗⼦进程想像成⼀个连体婴⼉,共享身体。这是 Linux 操作系统的机制,为了节约内存资源,所以尽可能让它们共享起来。在进程分离的⼀瞬间,内存的增⻓⼏乎没有明显变化。

COPY-ON-WRITE(写时复制)

        其核⼼思想是,如果有多个调⽤者(callers )同时请求相同资源(如内存或磁盘上的 数据存储 ),他们会共同获取相同的指针指向相同的资源,直到某个调⽤者试图修改资源的
内容时,系统才会真正复制⼀份专⽤副本( private copy )给该调⽤者,⽽其他调⽤者所⻅到的最初的资源仍然保持不变。
这⾥会有⼀个极端的情况,⽐如 Redis 内存⼤
⼩是 32 GB ,在某⼀个时刻,这 32GB 的数
据都被修改了,根据上⾯ COW 技术,那么就
需要把当前数据在复制⼀份,需要内存⼤⼩
32G 了,两个内存占⽤量就是 64GB ,所
以,我们在给 Redis 分配内存空间的时候,需
要注意,需要给 Redis 预留⼀些空间内存。
 

RDB的优缺点

RDB 的优点

体积更⼩:相同的数据量 RDB 数据⽐ AOF 的⼩,因为 RDB 是紧凑型⽂件。
恢复更快:因为 RDB 是数据的快照,基本上就是数据的复制,不⽤重新读取再写⼊内存。

性能更⾼:⽗进程在保存 RDB 时候只需要fork⼀个⼦进程,⽆需⽗进程的进⾏其他io操作,也保证了服务器的性能。

RDB 的缺点

故障丢失:因为 RDB 是全量的,我们⼀般是使⽤ shell 脚本实现 30 分钟或者 1 ⼩时或者每天对 Redis 进⾏ RDB 备份,
(注,也可以是⽤⾃带的策略),但是最少也要 5 分钟进⾏⼀次的备份,所以当服务死掉后,最少也要丢失 5 分钟的数据。
耐久性差:相对 AOF 的异步策略来说,因为 RDB 的复制是全量的,即使是 fork 的⼦进程来进⾏备份,当数据量很⼤的时
候对磁盘的消耗也是不可忽视的,尤其在访问量很⾼的时候,主线程 fork 的时间也会延⻓,导致 cpu 吃紧,耐久性相对较
差。

2.AOF持久化机制

AOF 持久化:以独⽴⽇志的⽅式记录每次写命令,重启时再重新执⾏ AOF ⽂件中的命令达到回复数据的⽬的。 AOF 的主要作⽤是解决了数据持久化的实时性。
开启⽅式:
开启 AOF 功能需要设置配置: appendonly yes ,默认不开启。 AOF ⽂件名通过 appendfilename 配置设置,默认⽂件名是 appendonly.aof 。保存路径同 RDB 持久化⽅式⼀致,通过dir 配置指定。

系统调⽤writefsync说明:

        Write操作会触发延迟写机制。 Linux 在内核提供⻚缓冲区⽤来提⾼硬盘 IO 性能。 wirte 操作在写⼊系统缓冲区后直接返回。同步硬盘操作依赖 于系统调度机制。例如:缓冲区⻚空间写满或达到特定时间周期。同步⽂件之前,如果此时系统故障宕机,缓冲区内数据将丢失。
        fync针对单个⽂件操作(⽐如 AOF ⽂件),做强制硬盘同步, fsync 将阻塞直到写⼊硬盘完成后返回,保证了数据持久化

AOF追加阻塞

        当开启AOF 持久化时,常⽤的同步硬盘的策略是 everysec ,⽤于平 衡性能和数据安全性。对于这种⽅式,Redis 使⽤另⼀条线程每秒执 ⾏fsync 同步硬盘。当系统硬盘资源繁忙时,会造成 Redis 主线程阻 塞

阻塞流程分析:

1 )主线程负责写⼊ AOF 缓冲区
2 AOF 线程负责每秒执⾏⼀次同步磁盘操作,并记录最近⼀次同步时
3 )主线程负责对⽐上次 AOF 同步时间
如果距上次同步成功时间在 2 秒内,主线程直接返回。
如果距上次同步成功时间超过 2 秒,主线程将会阻塞,直到同步操作完
AOF重写操作
1 )执⾏ AOF 重写请求,如果当前进程正在执⾏ AOF 重写,请求不执⾏
并返回如下响应:
ERR Background append only file rewriting already in progress 如果当前进程正在执⾏ bgsave 操作,重写命令延迟到 bgsave 完成之后 再执⾏,返回如下响应: Background append only file rewriting scheduled
2 )⽗进程执⾏ fork 创建⼦进程,开销等同于 bgsave 过程
3 )主进程 fork 操作完成后,继续响应其他命令。所有修改命令依然写 AOF 缓冲区并根据 appendfsync 策略同步到硬盘,保证原有 AOF 机制 正确性 由于 fork 操作运⽤写时复制技术,⼦进程只能共享 fork 操作时的内 存数据。由于⽗进程依然响应命令, Redis 使⽤ “AOF 重写缓冲区 保存 这部 分新数据,防⽌新 AOF ⽂件⽣成期间丢失这部分数据
4 )⼦进程根据内存快照,按照命令合并规则写⼊到新的 AOF ⽂件。每 次批量写⼊硬盘数据量由配置 aof-rewrite-incremental-fsync 控制,默 认为 32MB ,防⽌单次刷盘数据过多造成硬盘阻塞
5 )新的 AOF ⽂件写⼊完成后,⼦进程发送信号给⽗进程,⽗进程更新 统计信息,具体⻅ info persistence 下的 aof_* 相关统计 ⽗进程把 AOF 重写缓冲区的数据写⼊到新的 AOF ⽂件 使⽤新 AOF ⽂件替换⽼⽂件,完成 AOF 重写

AOF的优缺点分析

AOF 的优点

数据保证:我们可以设置 fsync 策略,⼀般默认是 Everysec ,也可以设置每次写⼊追加,所以即使服务死掉了,也最多丢失⼀秒数据
⾃动缩⼩:当 AOF ⽂件⼤⼩到达⼀定程度的时候,后台会⾃动的去执⾏ AOF 重写,此过程不会影响主进程,重写完成后,新的写⼊将会写到新的 AOF 中,
旧的就会被删除掉。但是此条如果拿出来对⽐ RDB 的话还是没有必要算成优点,只是官⽹显示成优点⽽已。

AOF 的缺点

性能相对较差:它的操作模式决定了它会对 Redis 的性能有所损耗。(主线程写⽂档)
体积相对更⼤:尽管是将 AOF ⽂件重写了,但是毕竟是操作过程和操作结果仍然有很⼤的差别,体积也毋庸置疑的更⼤。
恢复速度更慢:因为要重新加载每条命令的执⾏,恢复速度⽐较慢

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com