redis缓存穿透

是指缓存和数据库中都没有的数据,而用户不断发起非正常url请求,如发起为id为“-1”的数据或id为特别大不存在的数据。缓存查不到会一直查到数据库,这时候就造成了数据库的压力导致奔溃。这时的用户很可能是攻击者,攻击会导致数据库压力过大。
解决方案

1、对空值缓存
如果一个查询返回的数据为空(不管是数据是否不存在,因为可能出现命中率不到的情况),我们仍然把这个空结果(null)进行缓存,这样用户下次不断访问就可以用缓存返回。设置空结果的过期时间会很短,最长不超过五分钟
缺点:对空值缓存面对查询的条件不断变化,就会显得无力,比如查询参数一直变化:-1,-2,-3…

2、设置可访问名单(白名单)
使用bitmaps类型定义一个可以访问的名单,名单id作为bitmaps的偏移量,每次访问和bitmap里面的id进行比较,如果访问id不在bitmaps里面,进行拦截,不允许访问。
比如我们提供查询的key值id只有:1 2 3 4 5 6 , 那我们设置到bitmap里面去,如果访问id不在bitmaps里面,拦截。不去缓存查和数据库查
缺点:每个访问都需要取bitmaps查询,效率低

3、采用布隆过滤器
(布隆过滤器(Bloom Filter)是1970年由布隆提出的。它实际上是一个很长的二进制向量(位图)和一系列随机映射函数(哈希函数)。布隆过滤器可以用于检索一个元素是否在一个集合中。它的优点是空间效率和查询时间都比一般的算法要好的多,具体知识看面试题的总结。将所有可能存在的数据哈希到一个足够大的bitmaps中,一个一定不存在的数据会被这个bitmaps拦截掉,从而避免了对底层存储系统的查询压力。
缺点:有一定的误识别率、命中率低和删除困难。因为哈希值会冲突!

4、进行实时监控
当发现Redis的命中率开始急速降低,需要排查访问对象和访问的数据,和运维人员配合,可以设置黑名单限制服务

何为布隆过滤器:

应用例子:

假如现在有10亿个随机数,怎么快速判断某个数是否存在?

传统方案,每个随机数放到HashMap中,然后map.containsValue(“查找的值”)判断是否存在。

问题:1个数据4字节,总共需要4G存储空间

使用布隆过滤器:使用位数组,不存储数据,而是存储是否存在的状态

Redis贯穿 redis穿透是什么意思_数据库


Redis贯穿 redis穿透是什么意思_Redis贯穿_02


优点:

1、空间利用率高,可以存储全局数据

2、并行散列运算时间快

缺点:

1、Hash有概率会冲突,会产生误判

2、位数组大小及其散列函数的选择复杂性高