当前位置: 首页 > news >正文

【Redis】什么是缓存穿透、击穿、雪崩?如何解决?

1.缓存穿透

定义:

缓存穿透是指查询一个不存在的数据,由于缓存中没有该数据,请求会直接落到数据库上。如果大量这样的请求同时发生,数据库可能会被压垮。

原因:

  • 恶意攻击: 攻击者故意请求大量不存在的数据。
  • 业务逻辑问题:某些查询条件本身就不存在有效数据。

解决方案:

1.缓存空值:

  • 如果查询结果为空,扔将空值缓存起来,并设置一个较短的过期时间。
if (data == null) {
    cache.put(key, "NULL", 60); // 缓存空值,过期时间为 60 秒
}

2.布隆过滤器(Bloom Filter):

使用布隆过滤器预先判断数据是否存在。如果布隆过滤器认为数据不存在,则直接返回,避免查询数据库。

if (!bloomFilter.mightContain(key)) {
    return null; // 数据肯定不存在
}

3.接口层校验:

  • 在接口层请求参数进行校验,过滤掉明显非法的请求。

2.缓存击穿:

定义:

缓存击穿是指某个热点数据在缓存中过期后,大量请求同时涌入,直接访问数据库,导致数据库压力骤增。

原因:

  • 热点数据突然失效
  • 大量请求同时访问该数据。

解决方案:

1.设置热点数据永不过期:

  • 对于热点数据,可以设置永不过期,或者定期异步更新缓存。

2.互斥锁

  • 当缓存失效时,使用分布式锁(如Redis的SETNX) 确保只有一个线程去查询数据库并更新缓存,其他线程等待。
if (cache.get(key) == null) {
    if (lock.tryLock()) { // 获取锁
        try {
            // 查询数据库并更新缓存
            cache.put(key, value);
        } finally {
            lock.unlock(); // 释放锁
        }
    } else {
        // 等待缓存更新完成
        Thread.sleep(100);
        return cache.get(key);
    }
}

3.提前更新缓存:

  • 在缓存即将过期时,提前异步更新缓存,避免缓存失效。

3.缓存雪崩:

定义:

缓存雪崩是指大量缓存数据在同一时间过期,导致大量请求直接访问数据库,数据库压力骤增,直接崩溃。

原因:

  • 缓存数据设置了相同的过期时间。
  • 缓存服务宕机。

解决方案:

1.设置不同的过期时间:

  • 为缓存数据设置随机的过期时间,避免大量缓存同时失效。
int expireTime = 60 + new Random().nextInt(60); // 过期时间在 60-120 秒之间
cache.put(key, value, expireTime);

2.缓存高可用:

  • 使用Redis集群主从复制,确保缓存服务的高可用性。
  • 比如:使用Redis Sentinel或Redis Cluster

3.限流和降级:

  • 在缓存失效时,使用限流(如令牌桶算法)和降级策略,保护数据库。

4.多级缓存:

  • 使用多级缓存(如本地缓存+分布式缓存),减少缓存雪崩的影响。
if (localCache.get(key) != null) {
    return localCache.get(key);
} else if (distributedCache.get(key) != null) {
    localCache.put(key, distributedCache.get(key));
    return distributedCache.get(key);
} else {
    // 查询数据库并更新缓存
}

总结:

请添加图片描述

相关文章:

  • 实验3:Vue.js组件实验
  • 【LangChain入门 3 Prompts组件】聊天提示词模板 ChatPromptTemplate
  • jmeter中,上传文件的MIME类型
  • JVM垃圾回收
  • 识别并脱敏上传到deepseek/chatgpt的文本文件中的身份证/手机号
  • 迅为RK3568开发板篇Openharmony配置HDF控制UART-实操-HDF驱动配置UART-UART应用开发-编写应用测试 APP
  • 降低时间复杂度---一起来ABC
  • 【leetcode100】搜索插入位置
  • 【OpenCV C++】如何快速 高效的计算出图像中大于值的像素个数? 遍历比较吗? No,效率太低!那么如何更高效?
  • Java中的消息中间件对比与解析:RocketMQ vs RabbitMQ
  • C++实现rabbitmq生产者消费者
  • 蓝桥杯2023年第十四届省赛真题-子矩阵
  • Windows 图形显示驱动开发-WDDM 3.0功能- 硬件翻转队列(五)
  • C语言每日一练——day_7
  • ASP3605抗辐照加固同步降压调节器——商业航天电源芯片解决方案新选择
  • 鸿蒙下载文件保存到手机本地公共文件夹下、将本地的沙箱目录文件,保存到公共目录,鸿蒙picker save保存文件为空(0字节)的问题
  • windows命令:创建和打开文件
  • React + Node.js实践 仿B站评论
  • JavaScript 编程:从基础到高级应用的全面探索
  • 嵌入式开发之STM32学习笔记day08
  • 央行回应美债波动:单一市场、单一资产变动对我国外储影响总体有限
  • 大家聊中国式现代化|陶希东:打造高水平安全韧性城市,给群众看得见的安全感
  • 人民日报社论:做新时代挺膺担当的奋斗者
  • 金正恩出席朝鲜人民军海军驱逐舰入水仪式
  • 阿联酋启动第三届全球航空奖评选,奖金总额达百万美元
  • 全国首例!上市公司董监高未履行公开增持承诺,投资者起诉获赔