redis 知识图谱
2022-10-30 17:38:07 24 举报
AI智能生成
redis 知识图谱
作者其他创作
大纲/内容
过期策略
实现
所有有过期时间的 key 都存在一个过期字典(expires dict)中
策略
惰性删除
访问 key 时发现过期则删除
性能好
造成空间浪费
定期删除
每隔一段时间随机抽取一定数量的 key 进行检查
如果过期的比例超过一定量,则继续
设定了执行的最大时间防止卡死
通过控制时长和频率来减少对 cpu 的影响
主从模式下过期
从库不会进行过期扫描,对过期的处理事被动的
需要等主库在 AOF 文件中添加一条 del 指令
内存淘汰
maxmemory
策略
noeviction 默认
不驱逐,直接返回错误
volatile-random
volatile-ttl
volatile-lru
volatile-lfu
allkeys-random
allkeys-lru
allkeys-lfu
淘汰算法
LRU
一个 24bit 的字段记录最后访问时间戳
在淘汰时对比一批的数据
LFU
与 lru 类似
还是那个字段,但是低 8bit 存访问次数,搞 16bit 存时间戳
使用
延迟队列
订单超时,操作超时等操作
zet 使用时间来当分数
大 key
影响
客户端超时阻塞
网络阻塞
阻塞工作线程
内存分布不均
删除方式
分批删除
异步 unlink
分布式锁
加锁
解锁
优点
性能好
简单
避免单点故障
缺点
主从复制模式下锁不可靠
redLock
客户端从超过半数(大于等于 N/2+1)的 Redis 节点上成功获取到了锁
客户端从大多数节点获取锁的总耗时(t2-t1)小于锁设置的过期时间
缓存设计
概念
缓存雪崩
大量缓存数据在同一时间过期(失效)
过期时间加上随机数
互斥锁,保证少量线程去读库
备用 key
异步更新缓存
让缓存永久有效,更新缓存通过后台进行
缓存失效后通过消息队列通知进行更新
Redis 故障宕机
服务熔断或请求限流机制
构建 Redis 缓存高可靠集群
缓存击穿
大量请求去读库
解决方案同缓存雪崩
缓存穿透
大量请求不在缓存里面
非法请求限制
缓存空值或默认值
通过布隆过滤器判断数据是否在
高可用
切片集群 Cluster
脑裂
解决
min-slaves-to-write
min-slaves-max-lag
16384 哈希槽
哨兵模式 Sentinel
判断节点故障
每秒给所有节点发生 PING 命令
主观下线
down-after-milliseconds 超时时间
超过指定时间节点即为主观下线
客观下线
quorum
当认为主下线的数量不小于指定值时
主从故障转移
候选者
当判断主下线后,自动成为候选者
向所有哨兵发送选举请求(is-master-down-by-addr)
选举
拿到半数以上的赞成票
还需要不小于 quorum
过程
从剩余的从节点中选一个
通过 down-after-milliseconds 剔除掉一些网络不好的节点
判断优先级(slave-priority)
判断复制进度
master_repl_offset
slave_repl_offset
判断 id 号
升级为主服务器
SLAVEOF no one
让其他从节点修改复制目标
SLAVEOF
通过发布订阅通知客户端
向 +switch-master 频道发布新主节点的 IP 地址和端口
监视旧主节点,上线后设置为从节点
发布订阅频道
下线事件
+sdown 实例进入主观下线
-sdown 实例退出主观下线
+odown 实例进入客观下线
-odown 实例进入客观下线
从库重新配置事件
+slave-reconf-sent
哨兵发送 SLAVEOF 命令重新配置从库
+slave-reconf-inprog
从库配置了新主库,但未同步完成
+skave-reconf-done
从库配置了新主库,切同步完成
新主库切换
+switch-master
主库地址发送变化
哨兵通信
__sentinel__:hello
哨兵互相发现使用
主从复制
第一次同步
建立连接
从给主发送 psync
runID 主 id(第一次为?)
offset 负责进度(第一次为-1)
主收到后用 FULLRESYNC 响应
主服务器同步数据数据给从服务器
主执行 bgsave 生成 RDB
从收到 RDB 后清空当前数据,载入 RDB 文件
replication buffer 缓冲区(保证数据一致性)
主服务器生成 RDB 期间
主服务器发生 RDB 期间
从服务器加载 RDB 期间
主服务器发送新写操作给从
把replication buffer 缓冲区中的数据发送给从服务器
命令传播
通过一个 TCP 长连接来传播命令
增量复制
应对长连接短时间断开时都全量复制的问题
流程
从发送 psync 给主(offset 不是-)
主服务器收到后响应 continue 通知从进行增量复制
主把断链期间的数据发生给从
repl_backlog_buffer
一个环形缓冲区
当从获取的数据在缓冲区中找不是会进行全量复制
数据类型
string
场景
缓存对象
计数
分布式锁
实现
SDS
可以保存文本和二进制数据
获取长度时间复杂度为 O(1)
API 安全不会缓冲区溢出
list
场景
消息队列
实现
quicklist
hash
场景
缓存对象
实现
数量小用 listpack
数量大用哈希表
set
场景
并集
交集
差集
共同关注
点赞
实现
hash 表
zset
场景
排行榜
排序
BitMap
场景
签到
登录状态
布隆过滤器
HyperLogLog
海量数据基数统计
GEO
地理位置信息
Stream
场景
消息队列
使用
消息保序:XADD/XREAD
阻塞读取:XREAD block
重复消息处理:Stream 在使用 XADD 命令,会自动生成全局唯一 ID
消息可靠性:消费者使用 XACK 确认消息
支持消费组形式消费数据
缺陷
消息丢失
AOF 写盘是设置为每秒或自动时可能会丢
主从切换时
消息堆积
超过最大长度时丢弃
数据结构
键值对数据库
dict 数组
dictEntry 节点结构
key String 对象
value 实际使用对象
实际数据结构
SDS
对 C 语言字符串对象进行优化
len 使获取长度时间复杂度为 O(1)
alloc 防止缓冲区溢出
flags 表示不同的字符串类型,节省孽畜
buf[] 实际数据
二进制安全,可以存\0
双向链表
优点
获取前后节点时间复杂度为 O(1)
获取头尾节点 O(1)
获取节点数量 O(1)
节点使用指针保存,可以保存不同类型的值
缺陷
无法很好利用 CPU 缓存,即内存访问局部性原理
内存开销比数组大
不能随机访问
压缩列表
优点
节省内存
有效利用 CPU 缓存,即局部性原理
缺陷
不保存过多元素
修改元素是需要从新分配内存空间
可能引发连锁更新
哈希表
标准 hash 设计
rehash
渐进式 rehash
在哈希表 1操作元素时,把元素移动到哈希表 2
在哈希表 1 中不会新增元素
触发条件
负载因子大于 1,没有执行 RDB 快照或没有进行 AOF 重写的时候
当负载因子大于等于 5 时
跳表
标准跳表实现
为什么不用平衡树
内存占用小
实现简单
范围查询操作简单
整数集合
就是一个整数数组
quicklist
就是压缩列表的链表
listpack
优化了压缩列表,不保存前面节点的长度
线程
单线程处理优势
大部分操作都在内存中完成
避免多线程竞争
IO 多路复用处理链接
性能瓶颈不在 cpu
实现
主线程
接收客户端请求
解析请求
进行数据操作
发送给客户端
关闭文件线程
当队列有任务后,后台线程会调用 close(fd) ,将文件关闭
aof 刷盘
异步释放内存
后台线程会 free(obj) 释放对象 / free(dict) 删除数据库所有对象 / free(skiplist) 释放跳表对象
6.0 多线程
在处理网络 IO时使用多线程
可通过配置设置读请求可以走多线程
持久化
方式
AOF
先执行写在记录日志
好处
避免检查
不会阻塞当前操作
风险
数据丢失
会阻塞其他操作
策略
Always
你一次都会记录
保证最大程度不丢数据
频繁写硬盘,性能差
Everysec
每秒刷新一次
宕机可能会丢失 1s 内数据
No
不干预,系统决定
性能好,但可能丢失很多数据
重写
实现
对每一个 key 进行压缩
后台子进程bgrewriteaof进行处理
RDB
实现
全量快照
子进程读取,父线程写时复制
混合
0 条评论
下一页