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

【白话Redis】缓存雪崩、穿透、击穿、失效和热点缓存重建

快速导航

  • Redis不可不知的故障现象
    • 一、缓存雪崩
      • 定义:
      • 解决方案:
    • 二、缓存穿透
      • 定义:
      • 解决方案一:
      • 解决方案二(更普遍的做法):
    • 三、缓存击穿
      • 定义:
      • 解决方案:
    • 四、缓存失效
      • Redis缓存失效的情况:
    • 五、热点缓存重建
      • 1. 预热机制
      • 2. 异步重建
      • 3. 分布式锁
      • 4. 缓存预热与更新策略
      • 5. 缓存降级与容错
      • 6. 其他考虑因素

Redis不可不知的故障现象

一、缓存雪崩

定义:

由缓存机器故障宕机,导致大量请求全部落到数据库,超出了数据库的处理能力极限,进而导致数据库压力增大、宕机的情况。

解决方案:

  • 事前:Redis集群部署,主从+哨兵,避免全盘奔溃
  • 事中:本地缓存 + 限流&降级,避免数据库压力过大宕机
  • 事后:Redis持久化,机器重启后可以自动从磁盘加载数据,恢复缓存数据

二、缓存穿透

定义:

大批量请求缓存和数据库中都不存在的数据,导致数据库压力变大,甚至宕机。

解决方案一:

查询的key比较集中的时候,可以在查询数据库结束后给缓存中写一个空值或者默认值进去。设置一个过期时间,避免后续的大量请求落到数据库。

解决方案二(更普遍的做法):

在系统和缓存之间使用布隆过滤器,将数据库中所有可能的数据哈希映射到布隆过滤器中。
在请求到布隆过滤器时判断:

  • 若请求数据的key不存在布隆过滤器中,直接返回不存在(可以确定该数据也一定不存在于数据库)
  • 若请求数据的key在布隆过滤器中存在,则继续查询缓存

三、缓存击穿

定义:

某个热点key访问非常频繁,且请求时间比较集中,是高并发场景。当这个key失效的瞬间,大量的请求直接落到数据库,导致数据库压力骤增,甚至宕机。

解决方案:

  • 基本不更新的热点数据,设置为永不过期
  • 更新不频繁且缓存刷新流程耗时较少的情况下,可以基于互斥锁保证较少量的请求落到数据库,并重新构建缓存,而其他线程在锁释放后可访问新缓存。
  • 缓存数据更新频繁或者缓存刷新耗时较长的情况下,可以利用设置定时任务在任务过期前主动重新构建缓存或延后过期时间,以保证请求能一直访问到缓存

四、缓存失效

Redis缓存失效的情况:

1. 过期时间到期:

  • Redis缓存可以设置过期时间,当缓存的过期时间到达后,缓存数据会自动失效。

  • 解决方案: 合理设置缓存的过期时间,避免缓存数据过早或过晚失效。同时,可以考虑使用动态过期时间策略,根据数据的实际使用情况调整过期时间。

2. 内存不足:

  • 当Redis的内存使用达到上限时,Redis会根据配置的淘汰策略(如LRU算法)自动删除部分缓存数据,以释放内存空间。
  • 解决方案: 监控Redis的内存使用情况,及时升级Redis的内存配置或优化缓存策略,如减少不必要的缓存数据、增加缓存的复用率等。

3. 手动删除:

  • 管理员或开发者可能会通过Redis客户端命令手动删除缓存数据。
  • 解决方案: 建立规范的缓存操作流程,确保只有授权人员才能对缓存进行删除操作。同时,可以通过日志记录缓存的删除操作,以便追溯和审计。

4. 服务器重启:

  • Redis服务器重启时,所有缓存数据会丢失(除非使用了持久化功能)。
  • 解决方案: 配置Redis的持久化功能(如RDB或AOF),确保在服务器重启后能够恢复缓存数据。

5. 数据更新:

  • 当缓存数据对应的数据库数据发生更新时,如果缓存没有及时更新,就会导致缓存失效。
  • 解决方案: 实现缓存与数据库数据的一致性同步机制,如使用消息队列或订阅数据库变更日志来实时更新缓存数据。

6. 分布式环境下的缓存失效:

  • 在分布式系统中,多个应用节点可能同时使用同一个Redis缓存。如果某个节点修改了缓存数据,其他节点的缓存可能会失效。
  • 解决方案: 使用分布式锁或其他同步机制来确保在分布式环境下缓存数据的一致性。

7. 缓存雪崩:

  • 当大量缓存数据同时失效时,大量请求会涌入数据库,可能导致系统崩溃。
  • 解决方案: 设置随机过期时间以避免缓存同时失效;使用多级缓存策略;实施缓存标记策略;通过主从复制和哨兵机制提高Redis的高可用性;使用第三方插件如RocketMQ自动更新缓存等。

解决方案总结

  • 合理设置缓存过期时间:根据数据的实际使用情况设置合理的过期时间。
  • 监控和优化内存使用:定期监控Redis的内存使用情况,并优化缓存策略以减少内存消耗。
  • 规范缓存操作:建立规范的缓存操作流程,确保只有授权人员才能对缓存进行删除等操作。
  • 配置持久化功能:启用Redis的持久化功能,确保在服务器重启后能够恢复缓存数据。
  • 实现缓存与数据库的一致性同步:通过消息队列或订阅数据库变更日志等方式实现缓存与数据库数据的一致性同步。
  • 应对分布式环境下的缓存失效:使用分布式锁或其他同步机制来确保缓存数据的一致性。
  • 防范缓存雪崩:采取多种策略来避免缓存雪崩的发生,如设置随机过期时间、使用多级缓存、实施缓存标记策略等。

五、热点缓存重建

1. 预热机制

  • 定义:在系统启动或重启时,提前将预测会频繁访问的热点数据加载到缓存中。
  • 实现方式:
    • 通过定时任务在系统启动时执行数据加载。
    • 利用系统启动时的初始化代码加载数据。
    • 通过模拟请求或默认请求来预热缓存。
  • 优势:避免了系统启动初期的缓存穿透问题,提高了系统的启动速度和稳定性。

2. 异步重建

  • 定义:当热点缓存失效时,不立即阻塞请求线程去重建缓存,而是通过异步任务或消息队列等方式来重建缓存。
  • 实现方式:
    • 在缓存失效时,发布一个缓存失效事件到消息队列。
    • 系统中设置一个监听器来监听这些事件,一旦监听到失效事件,就启动一个异步线程去重建缓存。
    • 异步线程可以从数据库中获取数据,并将数据写回缓存。
  • 优势:降低了对系统实时性能的影响,使系统能够平滑处理高并发请求。

3. 分布式锁

  • 定义:在缓存重建过程中,使用分布式锁来确保同一时间只有一个线程或进程在重建缓存。
  • 实现方式:
    • 当缓存失效时,尝试获取分布式锁。
    • 如果获取锁成功,则进行缓存重建操作;如果获取锁失败,则等待或重试。
    • 缓存重建完成后,释放分布式锁。
  • 优势:避免了多个线程或进程同时重建缓存导致的资源浪费和竞态条件。

4. 缓存预热与更新策略

  • 策略一:在系统启动或业务低峰期,通过预热机制加载热点数据。
  • 策略二:定期更新缓存中的热点数据,确保数据的新鲜度。可以使用定时任务或监控机制来触发更新操作。
  • 策略三:根据缓存的访问频率和数据的变化情况,动态调整缓存的过期时间和重建策略。

5. 缓存降级与容错

  • 缓存降级:在缓存重建过程中,如果发生错误或异常,可以实施缓存降级策略,如返回默认值、空值或缓存中的旧数据,以避免系统崩溃。
  • 容错机制:确保缓存系统具有容错能力,能够在遇到硬件故障、网络问题等异常情况时,仍能提供一定程度的服务。

6. 其他考虑因素

  • 数据一致性:在缓存重建过程中,需要确保缓存数据与数据库数据的一致性。可以采用双写、延时双删或订阅数据库变更日志等方式来实现。
  • 性能监控:对缓存的访问情况、命中率、重建时间等进行实时监控,以便及时发现并解决潜在的性能问题。

相关文章:

【白话Redis】缓存雪崩、穿透、击穿、失效和热点缓存重建

快速导航 Redis不可不知的故障现象一、缓存雪崩定义:解决方案: 二、缓存穿透定义:解决方案一:解决方案二(更普遍的做法): 三、缓存击穿定义:解决方案: 四、缓存失效Redis…...

flink增量检查点降低状态依赖实现的详细步骤

增量检查点启动恢复的时间是很久的,业务上不能接受,所以可以通过降低状态依赖来减少恢复的时间。 降低状态依赖 尽可能减少状态的复杂性和依赖关系,通过拆分状态或将状态外部化到其他服务中,从而降低恢复的开销。 实施措施&…...

Redis总结,是什么,干什么,怎么利用?

Redis(Remote Dictionary Server)是一个开源的内存数据库,遵守 BSD 协议,它提供了一个高性能的键值(key-value)存储系统,常用于缓存、消息队列、会话存储等应用场景 Redis主要特性 &#xff08…...

Vue3状态管理Pinia

Vue3 的 Pinia 使用指南 Pinia 是 Vue3 中官方推荐的状态管理库,作为 Vuex 的替代品,它更简洁易用,并且支持模块化、类型推断和 DevTools 集成。Pinia 非常适合在 Vue3 项目中管理全局状态。 1. 安装 Pinia 首先,我们需要在 Vu…...

box64 安装

ARM运行x86程序 docker安装 box64 安装方法 docker run --name a001 -itd --networkhost -v /www/wwwroot/docker/Box64/f:/f ubuntu:22.04 /bin/bash docker exec -it a001 bash cd /home //创建目录qq547176052 mkdir -p qq547176052 cd /home/qq547176052 apt update apt …...

OpenCV通过鼠标提前ROI(C++实现)

文章目录 鼠标绘制矩形提取ROI任意形状绘制提前ROI 废话不多说&#xff0c;直接上代码 鼠标绘制矩形提取ROI #include <iostream> #include <opencv2\opencv.hpp> #include <opencv2/highgui/highgui.hpp> #include <opencv2/core/core.hpp>us…...

6.1.数据结构-c/c++模拟实现堆上篇(向下,上调整算法,建堆,增删数据)

目录 一.堆(Heap)的基本介绍 二.堆的常用操作&#xff08;以小根堆为例&#xff09; 三.实现代码 3.1 堆结构定义 3.2 向下调整算法* 3.3 初始化堆* 3.4 销毁堆 3.4 向上调整算法* 3.5 插入数据 3.6 删除数据 3.7 返回堆顶数据 四.下篇内容 1.堆排序 2.TopK问题 一…...

【智能终端】HBuilder X 与微信开发者工具集成与调试实战

目录 1. 需求和理解库、框架、平台 1.1 需求 1.2 理解 2.3 库、框架、平台 2.3.1 库&#xff08;Library&#xff09; 2.3.2 框架&#xff08;Framework&#xff09; 2.3.3 平台&#xff08;Platform&#xff09; 2.3.4 总结 2. 使用 HBuilder X 创建第一个 uni-app 应…...

结构体的字节对齐方式(__attribute_pack(packed))#pragma pack())

结构体的字节对齐方式&#xff08;__attribute_pack(packed))&#pragma pack()) 1、编译器的字节对齐方式 当前编译器都有默认的字节对齐方式&#xff0c; struct PackedStruct {char a;int b;short c; };如上代码段中的结构体&#xff0c;在编译运行后发现他的大小并不…...

若依Ruoyi之智能售货机运营管理系统(新增运营运维工单管理)

idea抽取独立方法快捷键&#xff1a;ctrlaltm TaskDto.java package com.dkd.manage.service.impl;import java.time.Duration; import java.util.List; import java.util.stream.Collectors;import cn.hutool.core.bean.BeanUtil; import cn.hutool.core.collection.CollUti…...

ModuleNotFoundError: No module named ‘keras.layers.core‘怎么解决

问题 ModuleNotFoundError: No module named keras.layers.core&#xff0c;如图所示&#xff1a; 如何解决 将from keras.layers.core import Dense,Activation改为from tensorflow.keras.layers import Dense,Activation&#xff0c;如图所示&#xff1a; 顺利运行&#xf…...

C++(三)----内存管理

1.C/C内存分布 看下面这个问题&#xff08;考考你们之前学的咋样&#xff09;&#xff1a; int globalVar 1; static int staticGlobalVar 1; void Test() {static int staticVar 1;int localVar 1;int num1[10] {1, 2, 3, 4};char char2[] "abcd";char* pCh…...

使用 ShuffleNet 模型在 CIFAR-100 数据集上的图像分类

简介 在深度学习领域&#xff0c;图像分类任务是衡量算法性能的重要基准。本文将介绍我们如何使用一种高效的卷积神经网络架构——ShuffleNet&#xff0c;来处理 CIFAR-100 数据集上的图像分类问题。 CIFAR-100 数据集简介 CIFAR-100 数据集是一个广泛使用的图像分类数据集&…...

怎么利用短信接口发送文字短信

在当今这个快节奏的数字时代&#xff0c;即时通讯已成为人们日常生活和工作中不可或缺的一部分。而短信接口&#xff08;SMS Interface&#xff09;&#xff0c;作为传统与现代通讯技术结合的典范&#xff0c;凭借其高效、稳定、广泛覆盖的特性&#xff0c;在众多领域发挥着不可…...

【C#生态园】提升C#开发效率:掌握这六款单元测试利器

从xUnit到SpecFlow&#xff1a;C#测试驱动开发全指南 前言 在C#开发中&#xff0c;单元测试和模拟框架是至关重要的工具&#xff0c;它们可以帮助开发人员确保代码的质量和可靠性。本文将介绍一些常用的C#单元测试框架和相关库&#xff0c;包括xUnit、NUnit、Moq、FluentAsse…...

【QT】自制一个简单的小闹钟,能够实现语音播报功能

做了一个自制的小闹钟&#xff0c;能够自己输入时间&#xff0c;以及对应的闹铃&#xff0c;时间到了自动播放设定的闹铃&#xff0c;可以随时取消重新设定&#xff0c;采用分文件编译 注意&#xff1a;需要在.pro文件中加入&#xff1a;QT core gui texttospeech 代码…...

基于深度学习的图像描述生成

基于深度学习的图像描述生成&#xff08;Image Captioning&#xff09;是一种将计算机视觉与自然语言处理结合的任务&#xff0c;其目标是通过自动生成自然语言来描述输入的图像。该技术能够理解图像中的视觉内容&#xff0c;并生成相应的文本描述&#xff0c;广泛应用于视觉问…...

Linux和C语言(Day11)

一、学习内容 讲解有参函数 形参 和 实参 形参——定义时的参数&#xff0c;形式上的参数&#xff0c;没有实际意义&#xff0c;语法上必须带有数据类型 void fun(int a,int b); void fun(int a[],int n); void fun(char *s); 可以是&#xff1a;变量、数组、指针 实参——调用…...

使用Zlib库进行多文件或者多文件夹的压缩解压缩

zlib库可在git上自己clone下来然后使用cmake工具生成解决方案&#xff0c;编译、生成zlib二进制文件。然后将zlib库引入项目&#xff1a; //zlib库支持 #include "../zlib/include/zlib.h" #ifdef _DEBUG #pragma comment(lib, "../zlib/lib/zlibd.lib") …...

CSGHub携手Nvidia NIM、阿里计算巢打造企业级私有化部署解决方案

强强联合 人工智能与大数据的迅速发展&#xff0c;大模型的推理应用和资产管理已成为企业数字化转型的重要组成部分&#xff0c;企业正寻求高效、安全的AI模型部署解决方案。为应对日益增长的计算需求和复杂的数据管理挑战&#xff0c;CSGHub、Nvidia和阿里云计算巢强强联手&a…...

后进先出(LIFO)详解

LIFO 是 Last In, First Out 的缩写&#xff0c;中文译为后进先出。这是一种数据结构的工作原则&#xff0c;类似于一摞盘子或一叠书本&#xff1a; 最后放进去的元素最先出来 -想象往筒状容器里放盘子&#xff1a; &#xff08;1&#xff09;你放进的最后一个盘子&#xff08…...

Python:操作 Excel 折叠

💖亲爱的技术爱好者们,热烈欢迎来到 Kant2048 的博客!我是 Thomas Kant,很开心能在CSDN上与你们相遇~💖 本博客的精华专栏: 【自动化测试】 【测试经验】 【人工智能】 【Python】 Python 操作 Excel 系列 读取单元格数据按行写入设置行高和列宽自动调整行高和列宽水平…...

Java - Mysql数据类型对应

Mysql数据类型java数据类型备注整型INT/INTEGERint / java.lang.Integer–BIGINTlong/java.lang.Long–––浮点型FLOATfloat/java.lang.FloatDOUBLEdouble/java.lang.Double–DECIMAL/NUMERICjava.math.BigDecimal字符串型CHARjava.lang.String固定长度字符串VARCHARjava.lang…...

页面渲染流程与性能优化

页面渲染流程与性能优化详解&#xff08;完整版&#xff09; 一、现代浏览器渲染流程&#xff08;详细说明&#xff09; 1. 构建DOM树 浏览器接收到HTML文档后&#xff0c;会逐步解析并构建DOM&#xff08;Document Object Model&#xff09;树。具体过程如下&#xff1a; (…...

跨链模式:多链互操作架构与性能扩展方案

跨链模式&#xff1a;多链互操作架构与性能扩展方案 ——构建下一代区块链互联网的技术基石 一、跨链架构的核心范式演进 1. 分层协议栈&#xff1a;模块化解耦设计 现代跨链系统采用分层协议栈实现灵活扩展&#xff08;H2Cross架构&#xff09;&#xff1a; 适配层&#xf…...

SpringCloudGateway 自定义局部过滤器

场景&#xff1a; 将所有请求转化为同一路径请求&#xff08;方便穿网配置&#xff09;在请求头内标识原来路径&#xff0c;然后在将请求分发给不同服务 AllToOneGatewayFilterFactory import lombok.Getter; import lombok.Setter; import lombok.extern.slf4j.Slf4j; impor…...

安卓基础(aar)

重新设置java21的环境&#xff0c;临时设置 $env:JAVA_HOME "D:\Android Studio\jbr" 查看当前环境变量 JAVA_HOME 的值 echo $env:JAVA_HOME 构建ARR文件 ./gradlew :private-lib:assembleRelease 目录是这样的&#xff1a; MyApp/ ├── app/ …...

九天毕昇深度学习平台 | 如何安装库?

pip install 库名 -i https://pypi.tuna.tsinghua.edu.cn/simple --user 举个例子&#xff1a; 报错 ModuleNotFoundError: No module named torch 那么我需要安装 torch pip install torch -i https://pypi.tuna.tsinghua.edu.cn/simple --user pip install 库名&#x…...

Netty从入门到进阶(二)

二、Netty入门 1. 概述 1.1 Netty是什么 Netty is an asynchronous event-driven network application framework for rapid development of maintainable high performance protocol servers & clients. Netty是一个异步的、基于事件驱动的网络应用框架&#xff0c;用于…...

【学习笔记】erase 删除顺序迭代器后迭代器失效的解决方案

目录 使用 erase 返回值继续迭代使用索引进行遍历 我们知道类似 vector 的顺序迭代器被删除后&#xff0c;迭代器会失效&#xff0c;因为顺序迭代器在内存中是连续存储的&#xff0c;元素删除后&#xff0c;后续元素会前移。 但一些场景中&#xff0c;我们又需要在执行删除操作…...