Nginx+Redis+Ehcache:大型高并发与高可用的三层缓存架构总结

  • 时间:
  • 浏览:0

redis cluster支撑多master node,每个master node还需要挂载多个slave node,机会mastre挂掉会自动将对应的某个slave切加上master。需要注意的是redis cluster架构下slave节点主就让我用来做高可用、故障主备切换的,机会一定需要slave都还能否 提供读的能力,修改配置也还需要实现(同去也需要修改jedis源码来支持该状况下的读写分离操作)。redis cluster架构下,master就让我还需要任意扩展的,直接横向扩展master即可提高读写吞吐量。slave节点都还能否 自动迁移(让master节点尽量平均拥有slave节点),对整个架构过载冗余的slave就还需要保障系统更高的可用性。

缓存穿透出理 方案

摘要: 对于高并发架构,毫无什么的疑问缓存是最重要的一环,对于少量的高并发,还需要采用三层缓存架构来实现,nginx+redis+ehcache

replication

出理 方案:将数据库与缓存更新与读取操作进行异步串行化。当更新数据的就让,根据数据的唯一标识,将更新数据操作路由到一一一个多jvm内控 的队列中,一一一个多队列对应一一一个多工作线程,线程串行拿到队列中的操作每根每根地执行。当执行队列中的更新数据操作,删除缓存,假使 去更新数据库,此时还还能否 完成更新的就让过来一一一个多读请求,读到了空的缓存还能否 还需要先将缓存更新的请求发送至路由就让的队列中,此日后 在队列积压,假使 同步等待缓存更新完成,一一一个多队列中多个相同数据缓存更新请求串在同去是还能否 意义的,假使 还需要做过滤出理 。等待前面的更新数据操作完成数据库操作就让,才会去执行下一一一个多缓存更新的操作,此日后 从数据库中读取最新的数据,假使 写入缓存中,机会请求还等待范围内,不断轮询发现还需要取到缓存中值就还需要直接返回(此时机会会有对你你这个 缓存数据的多个请求正在那我出理 );机会请求等待事件超过一定时长,还能否 你你这个 次的请求直接读取数据库中的旧值

二、redis集群

什么的疑问:机会先修改数据库再删除缓存,还能否 当缓存删除失败来,还能否 会原因数据库中是最新数据,缓存中依旧是旧数据,造成数据不一致。

当系统第一次启动,少量请求涌入,此时的缓存为空,机会会原因DB崩溃,进而让系统不可用,同样当redis所有缓存数据异常丢失,也会原因该什么的疑问。假使 ,还需要提前放上数据到redis出理 上述冷启动的什么的疑问,当然就让我机会是全量数据,还需要根据这类于当天的具体访问状况,实时统计出访问频率较高的热数据,这里热数据也比较多,需要多个服务并行的分布式去读写到redis中(就让要基于zk分布式锁)

对于流量挂接nginx,访问对应的数据,机会发现是热点标识就立即做流量挂接策略的降级,对同一一一个多数据的访问从hash到一台应用层nginx降级成为挂接至所有的应用层nginx。storm需要保存上一次识别出来的热点List,并同当前计算出来的热点list做对比,机会机会删剪日后 热点数据,则发送对应的http请求至流量挂接nginx中来收回对应数据的热点标识

sentinal哨兵

出理 方案:还需要先删除缓存,再修改数据库,机会删除缓存成功假使 数据库修改失败,还能否 数据库中是旧数据,缓存是空不让冒出不一致

Redis

哨兵是redis集群架构中很糙要的一一一个多组件,负责监控redis master和slave线程不是正常工作,当某个redis实例故障时,都还能否 发送消息报警通知给管理员,当master node宕机都还能否 自动转移到slave node上,机会故障转移趋于稳定来,会通知client客户端新的master地址。sentinal大概需要一个多实例来保证买车人的健壮性,假使 都还能否 更好地进行quorum投票以达到majority来执行故障转移。

RDB

一、模板引擎

欢迎工作一到五年的Java工程师其他同学歌词 们加入Java架构开发:880113481

热点数据的路由导师请求的倾斜:机会还能否 在商品数据更新的就让才会清空缓存,假使 才会原因读写并发,就让更新频率删剪日后 太高一句话,你你这个 什么的疑问的影响并删剪日后 很糙大,假使 的确机会或多或少机器的负载会高或多或少

缓存热点原因系统不可用出理 方案

实战踩坑:对于想从RDB恢复数据,同去AOF开关也是打开的,时不时无法正常恢复,机会每次日后 优先从AOF获取数据(机会临时关闭AOF,就还需要正常恢复)。此时首先停止redis,假使 关闭AOF,拷贝RDB到相应目录,启动redis就让热修改配置参数redis config set appendonly yes,此日后 自动生成一一一个多当前内存数据的AOF文件,假使 再次停止redis,打开AOF配置,再次启动数据就正常启动

Nginx缓存失效原因redis压力倍增

分布式缓存重建并发冲突出理 方案

对于缓存生产服务,机会部署在多台机器,当redis和ehcache对应的缓存数据都过期不趋于稳定时,此时机会nginx过来的请求和kafka监听的请求同去到达,原因两者最终都去拉取数据假使 存入redis中,假使 机会产生并发冲突的什么的疑问,还需要采用redis机会zookeeper这类的分布式锁来出理 ,让请求的被动缓存重建与监听主动的缓存重建操作出理 并发的冲突,当存入缓存的就让通过对比时间字段废弃掉旧的数据,保存最新的数据到缓存

缓存冷启动以及缓存预热出理 方案

redis cluster

群内提供免费的Java架构学习资料(上面有高可用、高并发、高性能及分布式、Jvm性能调优、Spring源码,MyBatis,Netty,Redis,Kafka,Mysql,Zookeeper,Tomcat,Docker,Dubbo,Nginx等多个知识点的架构资料)合理利用买车人每一分每一秒的时间来学习提升买车人,不让再用"还能否 时间“来掩饰买车人思想上的懒惰!趁年轻,使劲拼,给未来的买车人一一一个多交代!

tomcat jvm堆内存缓存,主就让我抗redis冒出大规模灾难。机会redis冒出了大规模的宕机,原因nginx少量流量直接涌入数据生产服务,还能否 最后的tomcat堆内存缓存也还需要出理 每项请求,出理 所有请求都直接流向DB

更新的就让,先删除缓存,假使 再更新数据库

对于你你这个 出理 法律方法需要注意或多或少什么的疑问:

对于上面件nginx常用来做流量的挂接,同去nginx本身删剪日后 买车人的缓存(容量有限),其他同学歌词 还需要用来缓存热点数据,让用户的请求直接走缓存并返回,减少流向服务器的流量

AOF

小型系统机会直接在服务器端渲染出所有的页面并放上缓存,就让的相同页面请求就还需要直接返回,不让去查询数据源机会做数据逻辑出理

持久化机制:将redis内存中的数据持久化到磁盘中,假使 还需要定期将磁盘文件上传至S3(AWS)机会ODPS(阿里云)等或多或少云存储服务上去。

以append-only的模式写入一一一个多日志文件中,在redis重启的就让还需要通过回放AOF日志中的写入指令来重新构建整个数据集。(实际上每次写的日志数据会先到linux os cache,假使 redis每隔一秒调用操作系统fsync将os cache中的数据写入磁盘)。对redis有一定的性能影响,都还能否 尽量保证数据的删剪性。redis通过rewrite机制来保障AOF文件不让太庞大,基于当前内存数据并还需要做适当的指令重构。

对于在多级缓存中都还能否 对应的数据,假使 DB就让能 查询到数据,此时少量的请求日后 直接到达DB,原因DB承载高并发的什么的疑问。出理 缓存穿透的什么的疑问还需要对DB就让能 的数据返回一一一个多空标识的数据,进而保存到各级缓存中,机会有对数据修改的异步监听,就让当数据有更新,新的数据会被更新到缓存汇中。

redis集群彻底崩溃,缓存服务少量对redis的请求等待,占用资源,就让缓存服务少量的请求进入源头服务去查询DB,使DB压力过大崩溃,此时对源头服务的请求也少量等待占用资源,缓存服务少量的资源删剪耗费在访问redis和源服务无果,最后使自身无法提供服务,最终会原因整个网站崩溃。

多实例部署的请求路由:机会你你这个 服务会部署多个实例,还能否 需要保证对应的请求都通过nginx服务器路由到相同的服务实例上

缓存雪崩出理 方案

比较比较复杂的数据不一致什么的疑问分析

事中的出理 方案,部署一层ehcache缓存,在redis删剪实现状况下都还能否 抗住每项压力;对redis cluster的访问做资源隔离,出理 所有资源都等待,对redis cluster的访问失败时的状况去部署对应的熔断策略,部署redis cluster的降级策略;对源服务访问的限流以及资源隔离

对时效性不高的数据,当趋于稳定变更就让,采取MQ异步通知的法律方法,通过数据生产服务来监听MQ消息,假使 异步去拉取服务的数据更新tomcat jvm缓存和redis缓存,对于nginx本地缓存过期就让就还需要从redis中拉取新的数据并更新到nginx本地。

对redis中的数据执行周期性的持久化,每一刻持久化的删剪日后 全量数据的一一一个多快照。对redis性能影响较小,基于RDB都还能否 快速异常恢复

事前的出理 方案,搭建一套高可用架构的redis cluster集群,主从架构、一主多从,一旦主节点宕机,从节点自动跟上,假使 最好使用双机房部署集群。

什么的疑问:对于数据趋于稳定来变更,先删除缓存,假使 去修改数据库,此时数据库中的数据还还能否 修改成功,并发的读请求到来去读缓存发现是空,进而去数据库查询到此时的旧数据放上缓存中,假使 就让对数据库数据的修改成功来,就会造成数据不一致

数据库和redis缓存双写不一致的什么的疑问

还需要在nginx本地,设置缓存数据的就让随机缓存的有效期,出理 同一时刻缓存都失效而少量请求直接进入redis

对于瞬间少量的相同数据的请求涌入,机会原因该数据经过hash策略就让对应的应用层nginx被压垮,机会请求继续就会影响至或多或少的nginx,最终原因所有nginx冒出异常整个系统变得不可用。

通过nginx+lua将访问流量上报至kafka中,storm从kafka中消费数据,实时统计处每个商品的访问次数,访问次数基于LRU(apache commons collections LRUMap)内存数据价值形式的存储方案,使用LRUMap去存放是机会内存中的性能高,还能否 内控 依赖,每个storm task启动的就让基于zk分布式锁将买车人的id写入zk同一一一个多节点中,每个storm task负责完成买车人这里的热数据的统计,每隔一段时间就遍历一下你你这个 map,假使 维护一一一个多前800的数据list,假使 去更新你你这个 list,最后开启一一一个多后台线程,每隔一段时间比如一分钟都将排名的前800的热数据list同步到zk中去,存储到你你这个 storm task对应的一一一个多znode中去

机会同去使用RDB和AOF本身持久化机制,还能否 在redis重启的就让,会使用AOF来重新构建数据,机会AOF中的数据更加删剪,建议将本身持久化机制都开启,用AO F来保证数据不丢失,作为数据恢复的第一选用;用RDB来作不同程度的冷备,在AOF文件都丢失或损坏不可用的就让来快速进行数据的恢复。

二、双层nginx来提升缓存命中率

读请求长时阻塞:机会读请求进行来非常轻度的异步化,就让对超时的什么的疑问需要格外注意,超过超时时间会直接查询DB,出理 不好会对DB造成压力,假使 需要测试系统高峰期QPS来调整机器数以及对应机器上的队列数最终决定合理的请求等待超时时间

对于页面非常之多的系统,当模板有改变,上述法律方法就需要重新渲染所有的页面模板,毫无什么的疑问是不可取的。假使 配合nginx+lua(OpenResty),将模板单独保趋于稳定nginx缓存中,同去对于用来渲染的数据也趋于稳定nginx缓存中,假使 需要设置一一一个多缓存过期的时间,以尽机会保证模板的实时性

一主多从架构,主节点负责写,假使 将数据同步到或多或少salve节点(异步执行),从节点负责读,主要就让我用来做读写分离的横向扩容架构。你你这个 架构的master节点数据一定要做持久化,假使 ,当master宕机重启就让内存数据清空,还能否 就会将空数据一键复制到slave,原因所有数据消失

后端nginx用来缓存或多或少热点数据到买车人的缓存区(挂接层还能否 配置一一一个多吗)

事后的出理 方案:redis数据做了备份还需要直接恢复,重启redis即可;redis数据彻底失败来机会数据过旧,还需要快速缓存预热,假使 让redis重新启动。假使 机会资源隔离的half-open策略发现redis机会都还能否 正常访问,还能否 所有的请求将自动恢复

缓存数据更新策略

部署多个实例的服务,每次启动的就让就会去拿到上述维护的storm task id列表的节点数据,假使 根据taskid,一一一个多一一一个多去尝试获取taskid对应的znode的zk分布式锁,机会都还能否 获取到分布式锁,再去获取taskid status的锁进而查询预热状况,机会还能否 被预热过,还能否 就将你你这个 taskid对应的热数据list取出来,从而从DB中查询出来写入缓存中,机会taskid分布式锁获取失败,快速抛错进行下一次循环获取下一一一个多taskid的分布式锁即可,此时就让我多个服务实例基于zk分布式锁做协调并行的进行缓存的预热

对于部署多个nginx而言,机会不加入或多或少数据的路由策略,还能否 机会原因每个nginx的缓存命中率很低。假使 还需要部署双层nginx

读的就让,先读缓存,缓存还能否 一句话,还能否 就读数据库,假使 取出数据后放上缓存,同去返回响应

对时效性要求高的缓存数据,当趋于稳定变更的就让,直接采取数据库和redis缓存双写的方案,让缓存时效性最高。

好的反义词更新的就让就让我删除缓存,机会对于或多或少比较复杂有逻辑的缓存数据,每次数据变更都更新一次缓存会造成额外的负担,就让我删除缓存,让该数据下一次被使用的就让再去执行读的操作来重新缓存,这里采用的是懒加载的策略。举个例子,一一一个多缓存涉及的表的字段,在1分钟内就修改了20次,机会是80次,还能否 缓存跟新20次,80次;假使 你你这个 缓趋于稳定1分钟内就被读取了1次,假使 每次更新缓存就会有少量的冷数据,对于缓存符合28黄金法则,20%的数据,占用了80%的访问量

Nginx

基于nginx+lua+storm的热点缓存的流量挂接策略自动降级来出理 上述什么的疑问的冒出,还需要设定访问次数大于后95%平均值n倍的数据为热点,在storm中直接发送http请求到流量挂接的nginx上去,使其存入本地缓存,假使 storm日后 将热点对应的删剪缓存数据没发送到所有的应用nginx服务器上去,并直接存放上本地缓存。

ehcache

前本身架构法律方法最大的特点是,每个节点的数据是相同的,无法存取海量的数据。假使 哨兵集群的法律方法使用与数据量不大的状况

一、持久化机制

通常其他同学歌词 还需要配合使用freemaker/velocity等模板引擎来抗住少量的请求

经典的缓存+数据库读写的模式,cache aside pattern

用户的请求,在nginx还能否 缓存相应的数据,还能否 会进入到redis缓存中,redis还需要做到全量数据的缓存,通过水平扩展都还能否 提升并发、高可用的能力

针对上面的技术我特意挂接了一下,有就让技术删剪日后 靠几句话能讲清楚,就让干脆找其他同学歌词 录制了或多或少视频,就让什么的疑问嘴笨 答案很简单,假使 眼前 的思考和逻辑不简单,要做到知其然需要知其就让然。机会想学习Java工程化、高性能及分布式、深入浅出。微服务、Spring,MyBatis,Netty源码分析的其他同学歌词 还需要加我的Java进阶群:694549689,群里有阿里大牛直播讲解技术,以及Java大型互联网技术的视频免费分享给其他同学歌词 。

你你这个 过程值得其他同学歌词 去深入学习和思考。

挂接层nginx负责流量挂接的逻辑和策略,根据买车人定义的或多或少规则,比如根据productId进行hash,假使 对后端nginx数量取模将某一一一个多商品的访问请求固定路由到一一一个多nginx后端服务器上去

最初级的缓存不一致什么的疑问以及出理 方案