缓存雪崩-看完Redis缓存穿透-缓存击穿-面试官都跪了! (缓存雪崩缓存击穿)
一、前言
「是一个开源(BSD容许)的,内存中的数据结构存储系统,它可以用作数据库、缓存和信息两边件。」
Redis在缓存运行中还是很宽泛的,名目中也经常经常使用。基本上方试中必需都会问到,总结一下增强记忆哈!
在享用缓存带来的好处的同时,当然要防止这些不好的方面。
上方咱们一同来看看这三种状况的发生要素和处置打算!
「总结:这三种情 况都是在少量恳求来的时刻,Redis没有命中,恳求间接打到数据库,从而造成数据库挂掉!」
Redis缓存简图:
二、缓存穿透
1、发生要素
「少量恳求的key是不正当的,缓存中基本不存在(数据库中普通也不存在),造成这些恳求绕过缓存间接访问数据库,给数据库形成了渺小的压力,随时或许宕机。」
2、处置打算
3、详细打算
「设置缓存空值:」
redis有一特性能,可以把从数据库查问进去为空的也缓存到Redis中,也可以自己在代码中写,顺便加上过时时期,也可以性能过时时期,这样是全局都是这个过时时期了,不太倡导这样!
spring:cache:redis:cache-null-value:truetime-to-live:30s
「限度并发查问:」
@Cacheable(value={"category"},key="#root.methodName",sync=true)
「布隆过滤器:」
布隆过滤器(BloomFilter)是一种用于判别一个元素能否属于一个汇合的数据结构。它的重要特点是高效地判别元素能否存在于汇合中,且具备空间和时期效率高的优势。布隆过滤器不会存储实践的数据,而是经过一系列的哈希函数和位数组来判别元素的存在。
「当布隆过滤器判别元素不存在时,元素必定不存在,元素存在时,元素不必定存在!」
是不是有点绕,咱们在详细说一下:
布隆过滤器有必定的假阳性概率,即在判别元素存在时,有或许发生失误的结果。这是由于多个元素或许发生相反的哈希值,造成位数组中的位被设置为1。
「布隆过滤器一旦参与了元素,就不能删除,由于删除元素会影响其余元素的判别结果。」
普通引入guava中的BloomFilter来成功布隆过滤器!假设青睐用Hutool,也是有成功的!
上方小编给大家便捷的写个demo,大家感触一下!
「引入依赖」
<dependency><groupId>com..guava</groupId><artifactId>guava</artifactId><version>30.1-jre</version></dependency>
「性能布隆过滤器」
/***@authorwangzhenjun*@date2023/11/717:08*/@ConfigurationpublicclassBloomFilterConfig{//预期拔出的元素个数,从性能文件里拿privatestaticfinalIntegerEXPECTED_INSERTIONS=100000;//希冀的误判率,值越低,布隆过滤器计算时期越长,从性能文件里拿privatestaticfinalDoubleFPP=0.03;@BeanpublicBloomFilter<String>bloomFilter(){BloomFilter<String>filter=BloomFilter.create(Funnels.stringFunnel(Charset.forName("utf-8")),EXPECTED_INSERTIONS,FPP);returnfilter;}}
「便捷测试」
为了便捷,间接写在启动类上了,大家不要学哈!
@EnableAsync@MerScan("com.example.demonew.demo.mapper")@EnableTransactionManagement@SpringBootApplicationpublicclassDemoNewApplication{@AutowiredprivateBloomFilterbloomFilter;publicstaticvoidmn(String[]args){SpringApplication.run(DemoNewApplication.class,args);}@PostConstructpublicvoidinit(){bloomFilter.put("123");booleanb=bloomFilter.mightContain("123");System.out.println("能否存在:"+b);}}
三、缓存击穿
1、发生要素
「缓存击穿是指当缓存中某个热点key刚刚过时(普通缓和存穿透区别在于热点数据存在于数据库中),在热点数据从新放入缓存之前,瞬间少量的恳求绕过缓存,间接打到数据库,数据库随时宕机!」
并发访问热点key:多个并发恳求同时访问相反的缓存键
缓存战略疑问:设置了过于短的缓存过时时期,容易造成缓存频繁失效。
「普通出如今秒杀中,秒杀都会提早预热,设置key直到优惠完结才会过时!」
2、处置打算
3、详细打算
「缓存预热:」
在名目启动时,或许定时义务扫描启动预热!
「限度并发查问:」
@Cacheable(value={"category"},key="#root.methodName",sync=true)、
详细解释上方曾经说过了哈!
「接口限流、熔断、升级」
可以引入:Sentinel来协助咱们更好的限流、熔断、升级,这里就不详细展示了!
四、缓存雪崩
1、发生要素
「缓存雪崩是指缓存中少量key到了过时时期,造成少量的恳求间接打到数据库上,数据库随时宕机!」
2、处置打算
「这个多级缓存,能不加不加,加了就要求思索分歧性,参与很多复杂度!」
其实缓存击穿缓和存雪崩是很相似的,处置打算,大家也可以看进去很多相反的!这就引出下一个经常问到的疑问:
3、详细处置打算
关于Redis的哨兵搭建可以看一下之前写的文章,这里就不展示了!
关于多级缓存,可以引入本地缓存Caffeine。
4、补充
「缓存击穿缓和存雪崩的区别?」
缓存击穿是缓存中某个热点key不存在了,缓存雪崩是缓存中少量或许一切key都不存在了
他俩的基本区别在于一个是单个key,一个是多个甚至所有key!
五、缓存污染
这里补充一下,关于缓存污染的吧!
1、发生要素
缓存污染指缓存中一些访问次数很少的key,甚至只要一次性!然而缓存中会存储着,占用内存空间。随着时期越来越久,内存很快被占满,就要求开启淘汰战略去额外处置这些多余的key,影响redis性能。
2、处置打算
最重要还是要把不罕用的key找到,前面不在参与缓存,从基本上处置!
还会出如今多个节点之间的数据同步发生数据不一致时发生,这个物品不好防止,由于Redis是
AP(可用性和分区容忍性)
,在多节点时,一半以上同步成功时,就以为同步成功了!
六、缓存分歧性
引入了缓存就必要求坚持缓存的分歧性,不然加了缓存没有任何意义!
网上关于缓存分歧性的文章很多,什么提早双删等等。
这些都不如阿里Canal,这个是经过监听的BinLog日志,来去升级到缓存中!
七、总结
当天咱们深化详细的讨论了Redis缓存穿透、缓存击穿、缓存雪崩的发生要素和处置打算,补充了缓存污染缓和存分歧性。
是不是有了深入的印象,这些物品在企业级还是挺经常出现的,在面试环节中愈加经常出现。置信大家从头看到尾,关于面试必需是没有任何疑问的。
在企业级运行中,必定要详细状况详细剖析,不要自觉照搬,不必定适宜你们的需求。
如何简单理解 Redis 的缓存穿透、击穿和雪崩?
深入理解Redis缓存异常:穿透、击穿与雪崩的实战解析
Redis,这个强大的键值存储系统,凭借其高性能和广泛应用,已成为开发中的首选缓存解决方案。然而,它的强大背后也隐藏着可能引发灾难的缓存异常——缓存穿透、击穿和雪崩。让我们一起探讨这些异常的实质、原因以及应对策略,以确保系统的稳定运行。
1. 缓存雪崩:数据库压力的瞬间爆发
当大量请求同时涌入,本应由Redis缓存处理,却因数据过期或服务故障而转向数据库,这就形成了缓存雪崩。它的成因包括:大量数据同时过期或Redis服务故障导致请求并发。解决方案包括合理设置过期时间,采用随机或微调策略,以及双key策略和后台更新缓存机制,以减轻数据库压力。
2. 缓存击穿:热点数据的并发挑战
缓存击穿发生在高并发下,热点数据的缓存过期,导致短时间内大量请求冲击数据库。解决方法包括为热点数据设置无过期时间或互斥锁,确保更新缓存的同时避免其他请求直接访问数据库。
3. 缓存穿透:恶意攻击与数据验证
恶意请求利用不存在的数据引发无用查询,对数据库造成压力。预防措施包括参数校验和布隆过滤器,前者拦截非法请求,后者通过多个哈希函数减少冲突,快速判断数据是否存在。
4. 谋篇布局:优化策略
除了异常处理,优化方法如缓存预热和降级也至关重要。缓存预热确保关键数据在用户访问前预先加载,而缓存降级则在服务故障时选择性地提供数据,以避免系统崩溃。
总之,理解和掌握Redis缓存异常及应对策略,是保障高效、稳定系统的关键。通过合理设计和优化,我们可以让Redis这一强大的工具发挥出其应有的力量,避免潜在的风险,提升整体性能。
redis常见问题
1. 缓存击穿
缓存击穿是指一个请求要访问的数据,缓存中没有,但数据库中有的情况。这种情况一般都是缓存过期了。
但是这时由于并发访问这个缓存的用户特别多,这是一个热点 key,这么多用户的请求同时过来,在缓存里面没有取到数据,所以又同时去访问数据库取数据,引起数据库流量激增,压力瞬间增大,直接崩溃给你看。
所以一个数据有缓存,每次请求都从缓存中快速的返回了数据,但是某个时间点缓存失效了,某个请求在缓存中没有请求到数据,这时候我们就说这个请求就击穿了缓存。
针对这个场景,对应的解决方案一般来说有三种。
借助Redis setNX命令设置一个标志位就行。设置成功的放行,设置失败的就轮询等待。就是在更新缓存时加把锁
后台开一个定时任务,专门主动更新过期数据
比如程序中设置 why 这个热点 key 的时候,同时设置了过期时间为 10 分钟,那后台程序在第 8 分钟的时候,会去数据库查询数据并重新放到缓存中,同时再次设置缓存为 10 分钟。
其实上面的后台续命思想的最终体现是也是永不过期。
只是后台续命的思想,会主动更新缓存,适用于缓存会变的场景。会出现缓存不一致的情况,取决于你的业务场景能接受多长时间的缓存不一致。
2. 缓存穿透
缓存穿透是指一个请求要访问的数据,缓存和数据库中都没有,而用户短时间、高密度的发起这样的请求,每次都打到数据库服务上,给数据库造成了压力。一般来说这样的请求属于恶意请求。
解决方案有两种:
就是在数据库即使没有查询到数据,我们也把这次请求当做 key 缓存起来,value 可以是 NULL。下次同样请求就会命中这个 NULL,缓存层就处理了这个请求,不会对数据库产生压力。这样实现起来简单,开发成本很低。
3. 缓存雪崩
缓存雪崩是指缓存中大多数的数据在同一时间到达过期时间,而查询数据量巨大,这时候,又是缓存中没有,数据库中有的情况了。
防止雪崩的方案简单来说就是错峰过期。
在设置 key 过期时间的时候,在加上一个短的随机过期时间,这样就能避免大量缓存在同一时间过期,引起的缓存雪崩。
如果发了雪崩,我们可以有服务降级、熔断、限流手段来拒绝一些请求,保证服务的正常。但是,这些对用户体验是有一定影响的。
4. Redis 高可用架构
Redis 高可用架构,大家基本上都能想到主从、哨兵、集群这三种模式。
哨兵模式:
它主要执行三种类型的任务:
哨兵其实也是一个分布式系统,我们可以运行多个哨兵。
然后这些哨兵之间需要相互通气,交流信息,通过投票来决定是否执行自动故障迁移,以及选择哪个从服务器作为新的主服务器。
哨兵之间采用的协议是 gossip,是一种去中心化的协议,达成的是最终一致性。
选举规则:
免责声明:本文转载或采集自网络,版权归原作者所有。本网站刊发此文旨在传递更多信息,并不代表本网赞同其观点和对其真实性负责。如涉及版权、内容等问题,请联系本网,我们将在第一时间删除。同时,本网站不对所刊发内容的准确性、真实性、完整性、及时性、原创性等进行保证,请读者仅作参考,并请自行核实相关内容。对于因使用或依赖本文内容所产生的任何直接或间接损失,本网站不承担任何责任。