redis数据安全机制
why:
redis一般作为缓存使用,从而提供系统的整体性能。redis是以内存请求为主的nosql DB,在重启、或者宕机的情况,如何确保数据不丢失,并且快速恢复,是redis的一大挑战。
How:
redis主要有两大方案保障数据的安全,分别是:RDB(redis data base)和AOF(append only file)。
what:
RDB:
就是所谓的“内存快照”,记录了redis某个时间点的内存数据,并以文件的形式存储在磁盘中。在redis重启是,能够使用RDB直接恢复内存数据。执行流程如下:
这样就可以不用每次写操作,都需要写磁盘,只需要在某个时间点写一次数据就可以了,同时RDB 采用二进制 + 数据压缩的方式写磁盘,文件体积小,数据恢复速度快。但是会出现数据丢失的问题(2次快照之间的数据,并没有落到磁盘上)。如果RDB的频率很高,例如1S1次,会加重磁盘的负担,从而降低性能。
执行方式:有同步(save)和异步(bgsave)。
save是主线程执行的,会阻塞redis;
bgsave主线程会fork一个子线程来完成,刚fork出的子线程和主线程是数据和代码共享的(所以在进程分离的一瞬间,内存的增长几乎没有明显变化),只有在主线程有写操作时,才会产生不同的数据。如图:
为了确保子线程做快照时,主线程还能写入数据。采用的方案是COW(copy on write),即:当主线程执行写指令修改数据的时候,这个数据就会复制一份副本, bgsave 子进程读取这个副本数据写到 RDB 文件。
AOF:
只记录了redis中写操作的顺序指令。这样恢复时,只需将写操作执行一遍(也叫重放),数据就可以恢复了。
redis采用记录方案:
采用“写后日志”,即:先执行写操作,内存写成功后,再记录日志(对比是:写前日志(Write Ahead Log, WAL),即: 在实际写数据之前,将修改的数据写到日志文件中,故障恢复得以保证)。操作流程如下:
“写后日志”好处是:不需要做指令检查,对当前指令没有阻塞(但是写磁盘动作,可能影响下1条指令)。
日志格式:
「*3」:表示当前指令分为三个部分,每个部分都是 「$ + 数字」开头,紧跟后面是该部分具体的「指令、键、值」。数字」:表示这部分的命令、键、值占用多少字节大小。比如 「$3」表示这部分包含 3 个字节,也就是 「set」指令。具体如下图:
数据落盘方案:
always:同步写回,写指令执行完毕立马将 aof_buf缓冲区中的内容刷写到 AOF 文件。
everysec:每秒写回,写指令执行完,日志只会写到 AOF 文件缓冲区,每隔一秒就把缓冲区内容同步到磁盘。
no: 操作系统控制,写执行执行完毕,把日志写到 AOF 文件内存缓冲区,由操作系统决定何时刷写到磁盘。
where(方向):
1、AOF文件过大,影响恢复效率:
引入“AOF重写”机制。redis使用bgrewriteaof指令对AOF日志文件进行瘦身。
原理:redis启动一个子线程(bgrewriteaof)对内存进行遍历,从而生成一系列的操作指令,并将这些操作指令序列化到新AOF文件中(新的aof文件,是防止AOF重写失败污染了原来的数据)。序列化完毕后,会将开始序列化到当前时间的增量AOF文件,追加到新的AOF文件中。然后替换就的AOF文件。
在整个过程中,会产生2个AOF文件和1个内存数据拷贝。
操作过程:Redis 会将重写过程中的接收到的「写」指令操作同时记录到旧的 AOF 缓冲区和 AOF 重写缓冲区。等到拷贝数据的所有操作记录重写完成后,重写重写缓冲区中的最新操作记录也会写入新的AOF文件中。具体的流程如下:
适应场景:对于重复写操作多的场景尤其效果明显。如下图:三条 LPUSH 指令,经过 AOF 重写后生成一条。
2、RDB和AOF的混合方案(redis 4.0开始使用)
将 rdb 文件的内容和增量的 AOF 日志文件存在一起,AOF 日志文件中只记录RDB后的增量操作记录,则该文件会很小,方便redis快速恢复。
该种模式下,RDB的频率就可以变小了,增量使用AOF来记录。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· Manus爆火,是硬核还是营销?
· 终于写完轮子一部分:tcp代理 了,记录一下
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通