缓存层持久化

** 读缓存**

  • 分布式缓存
    先将所有的缓存数据集中存储在同一个地方,而非重复保存到各个服务器节点中,然后所有的服务器节点都从这个地方读取数据
    在这里插入图片描述
    在这里插入图片描述
    使用MongoDB的公司最少,目前,Redis比Memcached更流行:
    (1)数据结构:在使用Memcached保存List缓存对象的过程中,如果往List中增加一条数据,则首先需要读取整个List,再反序列化塞入数据,接着再序列化存储回Memcached。而对于Redis而言,这仅仅是一个Redis请求,它会直接帮助塞入数据并存储,简单快捷
    (2)持久化:对于Memcached来说,一旦系统宕机数据就会丢失。因为Memcached的设计初衷就是一个纯内存缓存
    (3)集群:Memcached的集群设计非常简单,客户端根据Hash值直接判断存取的Memcached节点。而Redis的集群因在高可用、主从、冗余、Failover等方面都有所考虑,所以集群设计相对复杂些,属于较常规的分布式高可用架构

  • 缓存何时存储数据

  • 使用缓存的逻辑如下。

  • 1)先尝试从缓存中读取数据。

  • 2)若缓存中没有数据或者数据过期,再从数据库中读取数据保存到缓存中。

  • 3)最终把缓存数据返回给调用方

  • 4)注意,存在数据库崩溃的情况,当大量缓存不存在的时候导致。

  • 数据库的崩溃可以分为3种情况
    1)单一数据过期或者不存在,这种情况称为缓存击穿。
    解决方案:第一个线程如果发现Key不存在,就先给Key加锁,再从数据库读取数据保存到缓存中,最后释放锁。
    如果其他线程正在读取同一个Key值,那么必须等到锁释放后才行。
    2)数据大面积过期或者Redis宕机,这种情况称为缓存雪崩。
    解决方案:设置缓存的过期时间为随机分布或设置永不过期即可。
    3)一个恶意请求获取的Key不在数据库中,这种情况称为缓存穿透。
    比如正常的商品ID是从100000到1000000(10万到100万之间的数值),那么恶意请求就可能会故意请求2000000以上的数据。这种情况如果不做处理,恶意请求每次进来时,肯定会发现缓存中没有值,那么每次都会查询数据库,虽然最终也没在数据库中找到商品,但是无疑给数据库增加了负担。
    这里给出两种解决办法。
    ①在业务逻辑中直接校验,在数据库不被访问的前提下过滤掉不存在的Key。
    ②针对恶意请求的Key存放一个空值在缓存中,防止恶意请求骚扰数据库。
    4)缓存预热:用户请求过来之前把数据都缓存到Redis中

  • 如何更新缓存: 更新数据库和更新缓存
    先删除缓存,更新数据库,再删除缓存

  • 缓存的高可用设计
    1)负载均衡:是否可以通过加节点的方式来水平分担读请求压力。
    2)分片:是否可以通过划分到不同节点的方式来水平分担写压力。
    3)数据冗余:一个节点的数据如果失效,其他节点的数据是否可以直接承担失效节点的职责。
    4)Failover:任何节点失效后,集群的职责是否可以重新分配以保障集群正常工作。
    5)一致性保证:在数据冗余、Failover、分片机制的数据转移过程中,如果某个地方出了问题,
    能否保证所有的节点数据或节点与数据库之间数据的一致性(依靠Redis本身是不行的)
    6)如果对缓存高可用有需求,可以使用Redis的Cluster模式

  • 缓存的监控
    缓存上线以后,还需要定时查看其使用情况,再判断业务逻辑是否需要优化
    在查看缓存使用情况时,一般会监控缓存命中率、内存利用率、慢日志、延迟、客户端连接数等数据

写缓存
写缓存的思路是后台服务接收到用户请求时,如果请求校验没问题,数据并不会直接落库,而是先存储在缓存层中,缓存层中写请求达到一定数量时再进行批量落库。
这里所说的缓存层实际上指的就是写缓存。它的意义在于利用写缓存比数据库高几个量级的吞吐能力来承受洪峰流量,再匀速迁移数据到数据库
数据库如果用批量插入语句,TPS也是可以非常高的,可能达到上万,这样不仅能防止数据库崩溃,还能确保用户的请求得到满足
在这里插入图片描述
在具体实施过程中要考虑6个问题。
1)写请求与批量落库这两个操作同步还是异步?
根据业务实际考虑
2)如何触发批量落库?
批量落库触发逻辑:
1)写请求满足特定次数后就落库一次,比如10个请求落库一次。
优点:是访问数据库的次数变为1/N,从数据库压力上来说会小很多。
不足:如果访问数据库的次数未凑齐N次,用户的预约就一直无法落库。
2)每隔一个时间窗口落库一次,比如每隔一秒落库一次。
优点:能保证用户等待的时间不会太久,
缺点:如果某个瞬间流量太大,在那个时间窗口落库的数据就会很多,多到在一次数据库访问中无法完成所有数据的插入操作(比如一秒内堆积了5000条数据),它们只能通过分批次来实现插入
3)两种方式一起使用
1)每收集一次写请求,就插入预约数据到缓存中,再判断缓存中预约的总数是否达到一定数量,达到后直接触发批量落库。
2)开一个定时器,每隔一秒触发一次批量落库
在这里插入图片描述

3)缓冲数据存储在哪里?
存放在本地内存中,
存放在分布式缓存中(比如Redis),
其中最简单的方式是存放在本地内存中
4)缓存层并发操作需要注意什么?
缓存层并发操作逻辑与冷热分离迁移冷数据的逻辑很相似
批量落库的实现逻辑:
1)当前线程从缓存中获取所有数据。
2)当前线程批量保存数据到数据库。
3)当前线程从缓存中删除对应数据(注意:不能直接清空缓存的数据,因为新的预约数据可能插入到缓存中了)
5)批量落库失败了怎么办?
在这里插入图片描述

6)Redis的高可用配置
Redis的数据备份
Redis主从功能
在这里插入图片描述
统一管理的Redis集群方案:
1)先使用简单的主从模式。
2)然后在Slave Redis里使用快照(30秒一次)+AOF(一秒一次)的配置。
3)如果Master Redis宕机了,千万不要直接启动,先把Slave Redis升级为Master Redis。
4)这时代码里已经有预案了,写缓存如果失败直接落库。
不过这个方案有个缺点,即一旦系统宕机,手动恢复时大家就会手忙脚乱,但数据很有保障。

  • Kafka是LinkedIn推出的开源消息中间件,它天生是为收集日志而设计的,而且具备超高的吞吐量和数据量扩展性,被称作无限堆积

  • Kafka的存储结构中每个Topic分区相当于一个巨型文件,而每个巨型文件又是由多个Segment小文件组成的。
    其中,Producer负责对该巨型文件进行“顺序写”,Consumer负责对该文件进行“顺序读”。
    可以把Kafka的存储架构简单理解为,Kafka写数据时通过追加数据到文件末尾来实现顺序写,读取数据时直接从文件中读,这样做的好处是读操作不会阻塞写操作,这也是其吞吐量大的原因。
    理论上只要磁盘空间足够,Kafka就可以实现消息无限堆积,因此它特别适合处理日志收集这种场景
    在这里插入图片描述

  • 目前流行的实时处理工具主要为Storm、Spark Streaming、Apache Flink
    Apache Flink,不仅因为它性能强(阿里采用这项技术后,活动期间一秒内能够处理17亿条数据),
    还因为它的容错机制能保证每条数据仅仅处理一次,而且它有时间窗口处理功能。
    在实际业务场景中,如果需要按照时间窗口统计数据,往往是根据消息的事件时间来计算。
    Apache Flink的特性恰恰是使用了基于消息的事件时间,而不是基于计算框架的处理时间,这也是它的另一个撒手锏

  • 不同流处理框架中采取不同的容错机制,能够保证不一样的一致性。

  • 1)At-Most-Once:至多一次,表示一条消息不管后续处理成功与否只会被消费处理一次,存在数据丢失的可能。

  • 2)Exactly-Once:精确一次,表示一条消息从其消费到后续的处理成功只会发生一次。

  • 3)At-Least-Once:至少一次,表示一条消息从消费到后续的处理成功可能会发生多次,存在重复消费的可能。

  • 架构的流程:

  • 1)后台服务端会记录所有的请求数据,存放到本地的日志文件。

  • 2)使用数据收集框架Logstash,从日志文件抽取原始的日志数据,不加工直接存放到Kafka当中。

  • 3)通过Apache Flink从Kafka中拉取原始的日志数据,并且经过业务加工,分别存放到Elasticsearch、HBase和MySQL中。

  • 4)Elasticsearch用来处理用户针对请求日志的查询请求,它将查询关键字段的值和请求ID存放到索引中,跟进查询关键字获得结果ID的列表,再通过结果ID去HBase中获取详细的请求数据。

  • 5)MySQL存放一些组合加工后的数据,用来做结算,结算的数据查询和处理请求量不大。
    在这里插入图片描述
    秒杀架构

  • 秒杀架构的原则:
    遵循商品不能超卖
    下单成功的订单数据不能丢失
    服务器和数据库不能崩溃
    尽量别让机器人抢走商品

  • 秒杀架构的设计方案就是一个不断过滤请求的过程。目标是尽量在上层处理用户请求,不让其往下层游动。

  • 在这里插入图片描述

  • 静态资源与负载均衡
    CDN:不用花费自己的服务器资源和带宽,且响应速度快。静态资源的压力拦截在系统分层的外面
    动态的请求3种实现方式。
    1)通过JS(JavaScript)在后台动态调用。可以把动态的数据与页面进行整合,然后再放入CDN。也可以把它放在Redis缓存中,
    2)JS访问服务器获取,针对获取服务器时间的这个请求,把它放在静态资源或负载均衡那层即可,这样用户请求就不会进入系统下游。
    3)放在Cookie中。
    总体来说,对于浏览页面的用户行为,需要把用户请求尽量拦截在CDN、静态资源或负载均衡侧,如果确实做不到,也要拦截在缓存中。

  • 网关页面如何将请求拦截在上游
    那在网关层面如何实现请求过滤呢?可以做3种限制。
    1)限定每个用户的访问频率,比如每5秒下单一次。nginx上就能快速完成配
    2)限定每个IP的访问频率。nginx上就能快速完成配。这种方式是为了避免有人通过机器人自动下单,导致错杀真实用户。
    3)把一个时间段内的请求拦截掉一定比例,或者只允许特定数量的请求进入后台服务器。这里可以使用限流的漏桶或令牌桶算法

  • 后台服务器过滤请求:目标已经不是如何过滤请求了,而是如何保证商品不超卖
    1)商品数据放入缓存Redis中(在秒杀期间不做上架或修改库存之类的业务操作,即不通过技术,而是通过业务流程来保证)
    2)订单写入缓存中
    3)订单批量落库
    4)Redis停止工作(挂掉)怎么办。
    比如读Redis中的库存时,如果失败了,那就让它直接去数据库扣减库存,把那些incr和decr的逻辑放到数据库去;
    若是把订单写入缓存的时候失败了,那就直接将订单数据写入数据库中,然后就不需要处理后面批量落库的逻辑了

  • 付款页面如何将请求拦截在上游
    这个环节,除了保障数据的一致性外,还有一个要点:
    如果业务逻辑中出现了一个订单未及时付款而被取消的情况,记得把数据库及Redis的库存加回去

  • 整体:静态资源服务器、网关、后台服务器均需要配置负载均衡,而缓存Redis和数据库均需要配置集群模式
    在这里插入图片描述

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

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

相关文章

【操作系统】信号Signal超详解|捕捉函数

🔥博客主页: 我要成为C领域大神🎥系列专栏:【C核心编程】 【计算机网络】 【Linux编程】 【操作系统】 ❤️感谢大家点赞👍收藏⭐评论✍️ 本博客致力于知识分享,与更多的人进行学习交流 ​ 如何触发信号 …

【剖析】为什么说RBF神经网络的误差为0

本文来自《老饼讲解-BP神经网络》https://www.bbbdata.com/ 机器学习中的模型非常的多,但如果要问有没有这样的一个模型,它的训练误差为0,那么就非RBF神经网络莫属了!下面我们来聊聊,为什么RBF神经网络的训练误差为0。…

了解请求参数与响应参数的区别:初学者指南

在 Web 的开发领域,无论你是前端开发还是后端开发人员,把握请求与响应参数的核心差异是极其重要的。这些参数在客户端和服务器之间的互动中扮演着关键角色。 请求参数的定义及类别 定义 当客户端向服务器提交信息时所使用的数据被称为请求参数。这些参…

【Docker】Docker下载安装_使用阿里云加速配置

1、下载安装 1.1前提条件 安装环境: 目前,CentOS 仅发行版本中的内核支持 Docker。Docker 运行在 CentOS 7 上,要求系统为64位、系统内核版本为 3.10 以上。Docker 运行在 CentOS-6.5 或更高的版本的 CentOS 上,要求系统为64位…

STM32上实现spwm调制原理分析

在STM32微控制器上实现SPWM(正弦脉宽调制,Sinusoidal Pulse Width Modulation)调制的核心是利用高频载波(三角波)与低频基波(正弦波)作比较得出。 那么在STM32里三角波和正弦波分别是什么&…

YzmCMS内核简约风非常不错的博客自媒体主题模板

本次发布的“Eric”主题模版文件中,已移除默认模版中一些非必要的模版,仅保留一些通用模版(首页、频道页、列表页、资源列表页、内容页、关于我/单页等),当前模版主题中提供的模版文件已经能够满足大部分网站使用。 YzmCMS内核简约风非常不错…

Java数据结构4-链表

1. ArrayList的缺陷 由于其底层是一段连续空间,当在ArrayList任意位置插入或者删除元素时,就需要将后序元素整体往前或者往后搬移,时间复杂度为O(n),效率比较低,因此ArrayList不适合做任意位置插入和删除比较多的场景…

明明设置允许跨域,为什么还会出现跨域请求的问题

一、问题 在微服务项目中,明明已经设置允许跨域访问: 为什么还会出现跨域请求问题? 二、为什么 仔细查看错误提示信息:When allowCredentials is true, allowedOrigins cannot contain the special value "*" since t…

Cesium如何高性能的实现上万条道路的流光穿梭效果

大家好,我是日拱一卒的攻城师不浪,专注可视化、数字孪生、前端、nodejs、AI学习、GIS等学习沉淀,这是2024年输出的第20/100篇文章; 前言 在智慧城市的项目中,经常会碰到这样一个需求:领导要求将全市的道路…

Jenkins定时构建自动化(二):Jenkins的定时构建

目录 ​编辑 一、 jenkins定时构建语法: 1. 语法规则: 2. 常见用法举例 3. 再次举例 接上一篇:Jenkins定时构建自动化(一):Jenkins下载安装配置:Jenkins定时构建自动化(一):Jenkins下载安装配置-CSDN博客 …

常见的LED显示屏拼接优缺点解析

LED显示屏拼接技术在现代显示技术中占据了重要地位。随着市场需求的不断增长,各种拼接屏技术也不断发展,每种技术都有其独特的优势和不足。本文将详细解析常见的几种拼接屏技术,包括LED显示屏拼接、投影DLP拼接和等离子PDP拼接。 LED显示屏拼…

STM32CubeIDE提示找不到头文件(No such file or directory)的解决办法

0 前言 最近在使用STM32CubeIDE时,发现为工程添加了头文件路径,但编译的时候还是报错,提示找不到头文件: 1 解决办法 1.1 为工程添加头文件路径 右键我们的工程,然后添加头文件路径(最好是相对路径&am…

秋招突击——第八弹——Redis是怎么运作的

文章目录 引言正文Redis在内存中是怎么存储的面试重点 Redis是单线程还是多线程面试重点 内存满了怎么办?面试重点 持久化介绍面试重点 RDB持久化面试重点 AOF日志面试重点 总结 引言 差不多花了两天把redis给过了,早上也只背了一半,完成回去…

如何发现Redis热Key,有哪些解决方案?

什么是 hotkey? 如果一个 key 的访问次数比较多且明显多于其他 key 的话,那这个 key 就可以看作是 hotkey(热 Key)。例如在 Redis 实例的每秒处理请求达到 5000 次,而其中某个 key 的每秒访问量就高达 2000 次&#x…

Linux基础二

目录 一,tail查看文件尾部指令 二,date显示日期指令 三,cal查看日历指令 四,find搜索指令 五,grep 查找指令 六,> 和>> 重定向输出指令 七, | 管道指令 八,&&逻辑控…

Android开发神器:OkHttp框架源码解析

NetworkInterceptors CallServiceInterceptor 1.RealInterceptorChain.proceed() 2.EventListener.callStart()也是在RealCall.execute()嵌入到Request调用过程, EventListener.callEnd()位于StreamAllocation中调用 3.Request.Builder url (String/URL/HttpUrl) header …

Linux常用

很早以前的 ls: 查看文件夹内所有文件 rz: windows的文件传到linux服务器 sz filename: 将文件下载到windows本地 ctrlinsert:复制 shiftinsert:粘贴 ctrlD:退出spark-shell 运行脚本并输出日志 nohup sh filename.sh > log.log 2>&1 & 查看日…

STM32玩转物联网07-WIFI实验

前言 上一节我们学习了串口的简单使用,本节我们增加难度,做一个demo通过AT指令控制ESP8266,使用DMA方式接收ESP8266发来的数据,后续我们便开始通过ESP8266连接物联网云平台,敬请关注。 一、准备 1. ESP8266硬件准备 准…

在C++中,构造器(Builder)模式的思考(《C++20设计模式》及常规设计模式对比)

文章目录 一、前言二、为什么需要Builder Pattern,Builder Pattern到底解决了什么实际问题?为什么不用set()方法?2.1 初学者有那些对象的属性初始化方法呢?2.1.1 构造函数的弊端2.1.1.1 对于属性的初始化只能是固定的顺序 2.1.2 用set()函数初…

兰州理工大学24计算机考研情况,好多专业都接受调剂,只有计算机专硕不接收调剂,复试线为283分!

兰州理工大学(Lanzhou University of Technology),位于甘肃省兰州市,是甘肃省人民政府、教育部、国家国防科技工业局共建高校,甘肃省高水平大学和“一流学科”建设高校;入选国家“中西部高校基础能力建设工…