Redis 7.x 系列【38】缓存预热、缓存雪崩、缓存穿透、缓存击穿

news2025/1/24 4:49:43

有道无术,术尚可求,有术无道,止于术。

本系列Redis 版本 7.2.5

源码地址:https://gitee.com/pearl-organization/study-redis-demo

文章目录

    • 1. 缓存预热
    • 2. 缓存雪崩
    • 3. 缓存穿透
    • 4. 缓存击穿

1. 缓存预热

关键词:预先加载热点数据

缓存预热是指在服务启动或者流量高峰期之前,提前将数据加载到缓存中。避免因为缓存事先没有数据,大量请求直接落入到数据库中。

可以通过以下几种方式进行缓存预热:

  • 应用启动时加载:应用启动还未提供对外服务之前,查询数据库并加载到缓存中
  • 运行过程中加载:应用运行过程中,加载热点数据到缓存中

在应用启动时进行加载缓存,是比较常用的一种方式,例如,系统配置、系统参数、菜单等业务数据,都会放在基础应用中,并在启动时全量加载到数据库中。

如果使用的是 Spring Boot 则更加方便,在其启动阶段,提供了各种钩子用于执行一些初始化操作:

  • 启动监听事件
  • @PostConstruct
  • CommandLineRunner ApplicationRunner
  • InitializingBean. afterPropertiesSet

在运行过程中加载热点数据,可以使用以下方式:

  • 定时加载:添加定时任务,在使用高峰期前加载缓存
  • 监听:使用事件监听或者消息队列,触发缓存加载

2. 缓存雪崩

关键词:缓存大面积失效

雪崩是指大量雪体崩塌,缓存雪崩是指同一时间大面积的缓存失效,从而导致大量请求直接落到数据库上,导致数据库压力过大甚至崩溃。

在这里插入图片描述
发生缓存雪崩的情况一般有:

  • 单点故障
  • 大量缓存同一时间失效

针对 Redis 单点故障,一般可以使用高可用部署方式,比如哨兵、集群模式。针对大量缓存同一时间失效的情况,一般可以采取以下措施:

  1. 限流:防止并发请求超过阈值,比如使用 Sentinel
  2. 错开失效时间:为每一个缓存数据设置不同的过期时间,并保持一定的随机性。
  3. 多级缓存:使用本地缓存+Redis 缓存,当一级缓存失效时,使用更高效的二次缓存。

3. 缓存穿透

关键词:查询一定不存在的数据

缓存穿透是指访问缓存和数据库都不存在的数据,未命中缓存时需要从数据库查询,数据库中也没有对应的数据则也不会写入缓存。这类请求始终都会去数据库查询,如果请求的量过大或存在恶意攻击,会导致数据库压力过大甚至崩溃。

在这里插入图片描述
正常来说,用户不会频繁的去访问不存在数据,如果存在这种情况,很有可能是受到了恶意攻击,除了在服务外部做好安全防护外,服务内部也需要做一些处理措施。

解决方案:

  1. 安全防护:使用防火墙、防攻击软件拦截恶意请求。
  2. 访问次数限制:使用限流组件,例如 10 秒内限制访问总次数为 3 次。
  3. 接口校验:访问接口层校验参数是否合法,例如, ID 为负数时,不去数据库查询直接返回。
  4. 空值或默认值缓存:当访问缓存和数据库都没有查询到值时,可以将空值或默认值写进缓存。相同的 key 下次查询时,会返回缓存数据,如果是不同的 key ,第一次还是会去查询数据库。并且还需要设置过期时间,以免缓存 key 越写越多。
  5. 布隆过滤器:设置白名单,在布隆过滤器存在的数据再执行后续请求,不存在的直接返回。设置黑名单,数据库已查询且不存在的数据放入到布隆过滤器,下次查询在黑名单中时,直接返回。

4. 缓存击穿

关键词:缓存刚好失效

缓存穿透是指缓存中的数据刚好失效时,如果有大量并发请求过来,同时判断到缓存为空,会导致同时去查询数据库,导致数据库压力过大甚至崩溃。

在这里插入图片描述

这种情况在旁路缓存模式中容易触发,因为该模式更新数据时会删除缓存。特别是热点缓存数据一旦被删除,就需要考虑缓存被“击穿”的问题。一般使用双检加锁策略,首先检查是否有缓存,没有缓存会执行到查询请求,这里加一个互斥锁,再次检查是否有缓存,两次检查都没有时,则查询数据库,并回写缓存中。

双检加锁伪代码如下:

        // 1. 第一次查询缓存
        Object value = redisTemplate.opsForValue().get("key001");
        if (value != null) {
            // 缓存命中
            return value;
        } else {
            // 缓存未命中 添加互斥锁
            synchronized (this) {
                // 2. 第二次查询缓存
                value = redisTemplate.opsForValue().get("key001");
                if (value != null) {
                    // 缓存命中 直接返回
                    return value;
                } else {
                    // 第二次缓存未命中,查询数据库并加载缓存中
                    value = "value"; // 模拟查询数据库
                    redisTemplate.opsForValue().set("key001", "value");
                    return value;
                }
            }
        }

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1988857.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

某MDM主数据管理系统与蓝凌OA系统集成案例

一、项目背景 某客户使用OA在集团中处于一个重要角色,集团内各流程业务数据都需要通过OA进行审批下发,同某MDM主数据之间进行数据的交互,员工、供应商、法人组织、会计科目等主数据流程,实现各业务板块系统间的业务联通&#x…

动手学深度学习V2每日笔记(使用块的网络VGG)

本文主要参考沐神的视频教程 https://www.bilibili.com/video/BV1Ao4y117Pd/spm_id_fromautoNext&vd_sourcec7bfc6ce0ea0cbe43aa288ba2713e56d 文档教程 https://zh-v2.d2l.ai/ 本文的主要内容对沐神提供的代码中个人不太理解的内容进行笔记记录,内容不会特别严…

postgregSQL配置vector插件

1.下载vector 下载vector:https://pgxn.org/dist/vector/0.5.1/ 放在:C:\Program Files\PostgreSQL\vector-0.5.1 2.安装Visual Studio 2022 下载:https://visualstudio.microsoft.com/zh-hans/downloads/ 安装Visual Studio是为了C编译环…

JL-杰理芯片-认识TA的SDK的第六天

通过修改代码无法解决的错误解决问题的方法: 从头开始一点点的配置,并运行。(配置的是标准SDK) 将无法修改的错误打印到xshell中,去看看是什么原因,就算不能理解,也要看看他运行了几次。 上电开机和按键开机1T1,2T1,一拖二

Together规则引擎 金融解决方案

目录 1.金融法规和期望正在发生变化,快速跟踪您的金融数字化变革!2.抵押贷款功能集(MFS)3.MFS 示例模型4.MFS 知识特点5.MFS特定功能 1.金融法规和期望正在发生变化,快速跟踪您的金融数字化变革! ogether规则引擎使金融机构能够简…

26.9 Django书籍管理练习

1. 搭建环境 1.1 创建数据库 Django本身不会自动创建数据库服务器或数据库实例, 这一步需要手动完成.可以使用Navicat可视化工具或者命令行创建library数据库, 编码格式为utf8_mp4.# 连接数据库 mysql -h localhost -P 3306 -u root -p123456# 创建library数据库并设置编码 c…

面试题:Java 集合类的遍历方式,如何一边遍历 一边删除?

问题一:你用过 Java 中的哪些集合类? ArrayList, LinkedList, HashMap, HashSet, TreeSet, Stack, Queue, PriorityQueue等 问题二:集合中遍历元素的方式? Collection 接口实现子类 1. List 集合 // list 集合public static …

【Linux】进程间通信(管道通信、共享内存通信)

一.什么是进程间通信 进程间通信这五个字很好理解,就是进程和进程之间通信。 那么为什么要有进程间通信呢? 1.数据传输:一个进程需要将它的数据发送给另一个进程 2.资源共享:多个进程之间共享同样的资源 3.通知事件:一…

如何制作自己的python .whl包(支持entry_points)

目录 代码目录结构如下截图所示:dir_test.py 源码如下:list/dir_list.py 源码如下:setup.py 文件源码生成.whl文件指令: 代码目录结构如下截图所示: dir_test.py 源码如下: import os import sys from pat…

RunAsDate(时间限制工具)

参考链接1 参考链接2 参考链接3 下载地址 ps:64位系统需要下载64的RunAsDate

LAMP架构详解

目录 一、Apache详解 1.1 简介 1.2 Apache功能 1.3 apache特点 1.4 三种工作模式 二、LAMP简介 2.1 LAMP平台概述 2.2 构建LAMP平台顺序 2.3 编译安装的优点 2.4 各组件的主要作用 三、wget命令 四、curl命令 五、压力测试工具 一、Apache详解 1.1 简介 Apache …

vue2,v-for中动态渲染本地的图片

一、描述 如果是正常在img标签的src上使用本地的url地址,是可以正常被渲染的,但是我们通过for的形式,动态渲染的话,就会通过网络请求的方式进行渲染,这个形式反而渲染不出来。 二、效果 这个效果,毋庸置…

LVS负载均衡集群部署之—NAT模式的介绍及搭建步骤

一、环境准备 1.准备三台rhel9服务器 服务器名称 主机名 ip地址备注LVS调度服务器lvs.timinglee.org eth0:172.25.254.100(外网) eth1:192.168.0.100(内网) 关闭selinux和防火墙webserver2网站服务器webserver1.timinglee.orgeth0:192.168.…

为什么高校开设微专业,建议搭建动作捕捉与数字人开发实训室?

随着近年来虚拟现实技术产业与元宇宙产业不断发展,动作捕捉技术成为元宇宙、VR/AR、影视动画、游戏、艺术创作、虚拟偶像等行业相关不可或缺的技术之一。各大院校为了探索新的教学模式,纷纷积极开设“微专业”,相比传统的虚拟仿真实训室来说&…

Linux进程调度与切换

目录 前言 Linux 2.6内核O(1)调度器 调度过程 调度算法 Linux 进程切换 前言 在Linux 2.6版本的内核中,进程调度器引入了O(1)调度器,这个调度器通过优先级队列、活跃队列和过期队列的机制来管理进程调度,虽然在现在已被更好的CFS调度器取代,但对于我…

中仕公考:2024年空军专业技能类文职人员公开招考公告

2024年空军专业技能类文职人员公开招考公告,有关事项公告如下: 一、招考岗位 主要有保管员、司机、炊事员、文印员、汽车修理工兼司机等专业技能三级以下岗位。 二、招考对象 符合岗位资格条件的社会人员(含高校应届毕业生、退役军人)。 根据军队有…

理解栈(Stack)及其在 C++ 中的应用【栈、数据结构】

在这篇博客中,我们将详细介绍栈(Stack)这一重要的数据结构,包括其基本概念、常用操作、C 中的实现,以及一些实际应用。 什么是栈? 栈是一种数据结构,它遵循“后进先出”(LIFO - La…

上海AI Lab 搭台,36个大模型一起角逐长上下文建模能力

现在的大模型论文简直像是在比长度,动不动就上百页!记得前阵子小编瞅见那份90页的Gemini技术报告,顿时脑袋嗡嗡作响。那会儿就幻想着:要是有个AI大脑来啃下这些"学术巨无霸",那岂不是爽歪歪? 没…

SpringDoc:一个用于自动生成API文档的工具

SpringDoc的使用 概述SpringDoc添加依赖配置 Springdoc创建 REST 控制器访问 API 文档添加注释和描述自定义配置常用注解 详细示例创建模型类创建REST控制器查看Swagger UI与OpenAPI 安全策略类型概述HTTPAPIKEYOAUTH2OPENIDCONNECTMUTUALTLS 请求头配置认证token代码实现验证 …

C++:C++11介绍

✨✨✨学习的道路很枯燥,希望我们能并肩走下来! 文章目录 目录 文章目录 前言 一、C11简介 二 统一的列表初始化 2.1 {} 初始化 2.2 std::initializer_list 三 声明 3.1 auto 3.2 decltype 3.3 nullptr 四 范围for循环 五 智能指针 六 STL中一些变化…