缓存经典问题:
1.缓存穿透:
查询一个不存在的数据,不能命中缓存,导致每次请求都要到DB去查询,可能导致数据库崩溃。
a.查询返回的数据为空,仍把这个空结果进行缓存,但过期时间会比较短;
b.布隆过滤器:将所有可能存在的数据哈希到一个足够大的bitmap中,一个一定不存在的数 据会被这个bitmap拦截掉,从而避免了对DB的查询。
c.设定缓存值合理范围,避免被黑客可以攻击穿透;
2.缓存击穿:
对于设置了过期时间的key,缓存在某个时间点过期的时候,恰好有大量对这个key的并发请求,可能导致大量并发的请求瞬间把数据库压垮
1.使用互斥锁:当缓存失效时,先使用如Redis的setnx去设置一个互斥锁,保证同时只有一 个线程能够更新缓存,其他等待或者返回空值。
2.永远不过期:物理不过期,但逻辑过期(后台异步线程去刷新:定时读取/消息队列通知)
3.缓存雪崩:
设置缓存时采用了相同的过期时间,缓存在某一时刻同时失效,导致大量请求访问数据库。与缓存击穿的区别:雪崩是多key,击穿是单key缓存
1.分散缓存失效时间:在原有的失效时间基础上增加一个随机值;
2.使用互斥锁,同上
3.永远不过期,同上
4.缓存热点:
发现热key:
方法一:凭借业务经验,进行预估哪些是热key
方法二:在客户端进行收集
方法三:在Proxy层做收集
方法四:用redis自带命令
(1)monitor命令,该命令可以实时抓取出redis服务器接收到的命令,然后写代码统计出热 key是啥。
(2)hotkeys参数,redis 4.0.3提供了redis-cli的热点key发现功能,执行redis-cli时加上– hotkeys选项即可。但是该参数在执行的时候,如果key比较多,执行起来比较慢。
解决方法:
(1)监控热key
(2)通知系统做处理
这个方案也很简单。不要让key走到同一台redis上不就行了。我们把这个key,在多个redis 上都存一份不就好了。接下来,有热key请求进来的时候,我们就在有备份的redis上随机选 取一台,进行访问取值,返回数据。