redis击穿 雪崩 穿透超详细解决方案梳理


Posted in Redis onMarch 17, 2022

Redis击穿

redis缓存击穿是指某一个非常热点的key(即在客户端搜索的比较多的关键字)突然失效了,这时从客户端发送的大量的请求在redis里找不到这个key,就会去数据里找,最终导致数据库压力过大崩掉。

redis击穿 雪崩 穿透超详细解决方案梳理

解决方案:

1.将value的时效设置成永不过期 这种方式非常简单粗暴但是安全可靠。但是非常占用空间对内存消耗也是极大。个人并不建议使用该方法,应该根据具体业务逻辑来操作。

2.使用Timetask做一个定时任务 使用Timetask做定时,每隔一段时间对一些热点key进行数据库查询,将查询出的结果更新至redis中。前条件是不会给数据库过大的压力。

3.通过synchronized+双重检查机制 当发生reids穿透的时候,这时海量请求发送到数据库。这时我们的解决办法是只让只让一个线程去查询这个热点key,其它线程保持阻塞状态(可以让它们sleep几秒)。当这个进入数据库的线程查询出key对应的value时,我们再将其同步至redis的缓存当中,其它线程睡醒以后再重新去redis里边请求数据。

例子:

private static volaite Object obj = new Object();
   public String getValue(String key){
     String value=redis.get(key,String.class);
     if(value==null||StringUtils.isBlank(value){
         synchronized(obj){
         		//进入synchronized以后再去redis里查一遍,防止上一个抢到锁的线程已经更新过了。
                value=redis.get(key,String.class);
                 if(value==null||StringUtils.isBlank(value){
                     value=db.query(key);
                      redis.set(key,value,1000); 
          }
       }
     }    
      return value;
   }

缺点:存在死锁和线程阻塞的风险。

Redis雪崩

指的是当海量的请求去查询多个key时,此时redis缓存中失效或者查不到,然后海量的请求都去都去db查询,从而导致db压力突然飙升崩溃。

出现原因:

1.key同时失效

2.redis本身崩溃了

redis击穿 雪崩 穿透超详细解决方案梳理

解决方案:

1.设置缓存时,随机初始化其失效时间

如果是redis的key同时失效,可采取该办法,具体失效时间根据业务情况决定…

2.将不同的热点key放置到不同的节点上去

因redis一般都是集群部署,将不同的热点key平均的放置到不同节点,也可以有效避免雪崩。

3.将value的时效设置成永不过期

4.使用Timetask做一个定时任务,在失效之前重新刷redis缓存

Redis穿透

因为不良用户恶意频繁查询才会对系统造成很大的问题: key缓存并且数据库不存在,所以每次查询都会查询数据库从而导致数据库崩溃。

(例如:我们在数据库存放的数据其主键都是自增且没有负数的,某些黑客就利用这一点,不断用主键id为-1的参数来发起海量查询请求,导致这些请求在redis中查不到相应的数据,只能去数据库中查询,从而导致数据库崩溃。)

redis击穿 雪崩 穿透超详细解决方案梳理

解决方案:

1.当类似的请求发过来,无论查出什么结果都放入redis缓存

这样解决当他下次再用同一个参数发起请求时,会直接进到redis里边去,不会再进入数据库。

2.拉黑其ip

3.对请求的参数进行合法性校验,在判断其不合法的前提下直接return掉

4.使用布隆过滤器

可以将布隆过滤器理解成一个白名单或者黑名单,它的作用就是判断一个元素是否存在于这个过滤器。

白名单: 过滤器里有数据库中所有的合法的参数key,请求经过布隆过滤器,布隆过滤器判断这个请求的key在不在过滤器,在就放行让请求进入redis,不在就直接return空数据。

redis击穿 雪崩 穿透超详细解决方案梳理

public static void main(String[] args){
	Config config = new Config();
	config.useSingleServer().setAddress("redis://127.0.0.1:6379");
	config.useSingleServer().setPassword("1234");
	//构造Redsson
	RedissonClient redisson = Redisson.create(config);
	RBloomFilter<String> bloomFilter = redisson.getBloomFilter("phoneList");//给我们自己定义的布隆过滤器取名叫phoneList,名字随便取
	//初始化布隆过滤器设置预计元素为100000000L, 误差率为3%
	bloomFilter.tryInit(100000000L,0.03);
	//将10086插入到布隆过滤器中
	bloomFilter.add("10086");
	//判断下面号码是否存在布隆过滤器中
	//false
	System.out.println("123456");
	//true
	System.out.println("10086");
}

缺点:

布隆过滤器可能会造成误判,从而穿透redis进入DB,但是这个误判概率是非常小的。

以上就是redis击穿 雪崩 穿透超详细解决方案梳理的详细内容,更多关于redis 击穿 雪崩 穿透的资料请关注三水点靠木其它相关文章!

Redis 相关文章推荐
浅谈redis五大数据结构和使用场景
Apr 12 Redis
基于Redis延迟队列的实现代码
May 13 Redis
详解Redis瘦身指南
May 26 Redis
浅谈Redis主从复制以及主从复制原理
May 29 Redis
redis不能访问本机真实ip地址的解决方案
Jul 07 Redis
缓存替换策略及应用(以Redis、InnoDB为例)
Jul 25 Redis
详解Redis在SpringBoot工程中的综合应用
Oct 16 Redis
Redis+Lua脚本实现计数器接口防刷功能(升级版)
Feb 12 Redis
Redis 中使用 list,streams,pub/sub 几种方式实现消息队列的问题
Mar 16 Redis
redis击穿 雪崩 穿透超详细解决方案梳理
Mar 17 Redis
Redis如何实现验证码发送 以及限制每日发送次数
Apr 18 Redis
Redis配置外网可访问(redis远程连接不上)的方法
Dec 24 Redis
Redis调用Lua脚本及使用场景快速掌握
Redis 的查询很快的原因解析及Redis 如何保证查询的高效
Redis 中使用 list,streams,pub/sub 几种方式实现消息队列的问题
Redis中有序集合的内部实现方式的详细介绍
Mar 16 #Redis
面试分析分布式架构Redis热点key大Value解决方案
分布式架构Redis中有哪些数据结构及底层实现原理
Redis之RedisTemplate配置方式(序列和反序列化)
Mar 13 #Redis
You might like
PHPUnit PHP测试框架安装方法
2011/03/23 PHP
PHP 安全检测代码片段(分享)
2013/07/05 PHP
PHP5.2下preg_replace函数的问题
2015/05/08 PHP
laravel5.6 框架操作数据 Eloquent ORM用法示例
2020/01/26 PHP
许愿墙中用到的函数
2006/10/07 Javascript
JavaScript中为元素加上name属性的方法
2011/05/09 Javascript
jWiard 基于JQuery的强大的向导控件介绍
2011/10/28 Javascript
基于jQuery的公告无限循环滚动实现代码
2012/05/11 Javascript
Jquery创建层显示标题和内容且随鼠标移动而移动
2014/01/26 Javascript
JS动态修改表格cellPadding和cellSpacing的方法
2015/03/31 Javascript
js实现超酷的照片墙展示效果图附源码下载
2015/10/08 Javascript
JavaScript判断按钮被点击的方法
2015/12/13 Javascript
AngularJS  $modal弹出框实例代码
2016/08/24 Javascript
Node.js包管理器Yarn的入门介绍与安装
2016/10/17 Javascript
jQuery插件FusionCharts绘制2D柱状图和折线图的组合图效果示例【附demo源码】
2017/04/10 jQuery
vue2.0 常用的 UI 库实例讲解
2017/12/12 Javascript
详解vue中this.$emit()的返回值是什么
2019/04/07 Javascript
js getBoundingClientRect使用方法详解
2019/07/17 Javascript
js实现随机点名器精简版
2020/06/29 Javascript
JavaScript canvas实现跟随鼠标移动小球
2021/02/09 Javascript
[07:47]DOTA2国际邀请赛采访专栏:探访Valve总部
2013/08/08 DOTA
[01:02:48]2018DOTA2亚洲邀请赛 4.1 小组赛 A组 LGD vs OG
2018/04/02 DOTA
Python多线程下载文件的方法
2015/07/10 Python
python与C互相调用的方法详解
2017/07/14 Python
python写入并获取剪切板内容的实例
2018/05/31 Python
Python递归函数实例讲解
2019/02/27 Python
python实现祝福弹窗效果
2019/04/07 Python
python实现单链表的方法示例
2019/09/03 Python
从多个tfrecord文件中无限读取文件的例子
2020/02/17 Python
澳大利亚潮流尖端的快时尚品牌:Cotton On
2016/09/26 全球购物
应届生骨科医生求职信
2013/10/31 职场文书
公司任命书模板
2014/06/06 职场文书
经典演讲稿开场白
2014/08/25 职场文书
政审证明材料
2015/06/19 职场文书
干部外出学习心得体会
2016/01/18 职场文书
MySQL 角色(role)功能介绍
2021/04/24 MySQL