(1)应用场景
解耦和
看这么个场景。A系统发送数据到BCD三个系统,通过接口调用发送如果E系统也要
这个数据呢?那如果C系统现在不需要了呢A系统负责人几乎崩溃
在这个场景中,A系统跟其它各种乱七八糟的系统严重耦合,A系统产生一条比较关键的
数据,很多系统都需要A系统将这个数据发送过来A系统要时时刻刻考虑BCDE四个系
统如果挂了该咋办?要不要重发,要不要把消息存起来头发都白了啊
如果使用MQ,A系统产生一条数据,发送到M里面去,哪个系统需要数据自己去M
里面消费如果新系统需要数据,直接从MQ里消费即可如果某个系统不需要这条数据
了,就取消对MQ消息的消费即可。这样下来,A系统压根儿不需要去考虑要给谁发送数
据,不需要维护这个代码,也不需要考虑人家是否调用成功、失败超时等情兄
总结:通过一个MQ,Pub/Sub发布订阅消息这么一个模型A系统就跟其它系统彻底解
耦了。
面试技巧:你需要去考虑一下你负责的系统中是否有类似的场景,就是一个系统或者一个模
块,调用了多个系统或者模块,互相之间的调用很复杂维护起来很麻但是其实这个调
用是不需要直接同步调用接口的,如果用MQ给它异步化解耦,也是可以的,你就需要去
考虑在你的项目里,是不是可以运用这个MQ去进行系统的解耦在简历中体现出来这块
东西,用MQ作解耦。
异步处理
再来看一个场景,A系统接收一个请求,需要在自己本地写库,还需要在BCD三个系统写
库,自己本地写库要3ms,BCD三个系统分别写库要300ms、450ms、200ms最终请求总
延时是3+300+450+200=953接近1,用户感觉搞个什么东西,慢死了慢死了。用
户通过浏览器发起请求,等待个1s,这几乎是不可接受的。
一般互联网类的企业,对于用户直接的操作,一般要求是每个请求都必须在200ms以内完
成,对用户几乎是无感知的。
如果使用MQ,那么A系统连续发送3条消息到M队列中假如耗时5ms系统从
接受一个请求到返回响应给用户,总时长是3+5=8m于用户而言其实感觉上就是
点个按钮,8ms以后就直接返回了,爽!网站做得真好,真快!
流削峰
每天0:00到12:00,A系统风平浪静,每秒并发请求数量就50个结果每次一到12:00
13:00,每秒并发请求数量突然会暴增到5k+条但是系统是直接基于MQL的,大里
的请求涌入 MysQL,每秒钟时 MysQL执行约5k条QL
一般的,打到每秒2k个请求就差不多了如果每秒请求到5k的话,可能就直接
把 MySaL给打死了,导致系统崩溃,用户也就没法再使用系统了。
但是高峰期一过,到了下午的时候,就成了低期,可能也就1的用户同时在网站上操
作,每秒中的请求数量可能也就50个请求,对整个系统几乎没有任何的压力
如果使用MQ,每秒5k个请求写入MQ,A系统每秒钟最多处理2k个请求,因为 MySQL
每秒钟最多处理2k个。A系统从MQ中慢慢拉取请求,每秒钟就拉取2k个请求,不要
超过自己每秒能处理的最大请求数就ok,这样下来,哪怕是高峰期的时候,A系统也绝
对不会挂掉。而MQ每秒钟5k个请求进来,就2k个请求出去,结果就导致在中午高峰
期(1个小时),可能有几十万甚至几百万的请求积压在MQ中。
这个短暂的高峰积压是ok的,因为高峰期过了之后每秒钟就50个请求进MQ,但是
A系统依然会按照每秒2k个请求的速度在处理。所以说,只要高峰期一过,A系统就会
快速将积压的消息给解决掉。
(2)消息队列缺点
21系统可用性降低
系统引入的外部依赖越多,越容易挂掉。本来你就是A系统调用BCD三个系统的接口就
好了,人ABCD四个系统好好的,没啥问题你偏加个MQ进来,万一MQ挂了咋整,
MQ一挂,整套系统崩溃的,你不就完了?如何保证消息队列的高可用
系统夏杂度提高
硬生生加个MQ进来,你怎么保证消息没有重复消费怎么处理消息丢失的情况?怎么保
证消息传递的顺序性?头大头大,问题一大堆,痛苦不已。
23一致性问题
A系统处理完了直接返回成功了,人都以为你这个请求就成功了但是问题是要是BCD三
个系统那里,BD两个系统写库成功了,结果系统写库失败了,咋整?你这数据就不一
致了。
所以消息队列实际是一种非常复杂的架构,你入它有很多好处,但是也得针对它带来的坏
处做各种额外的技术方案和架构来规避掉,做之后,你会发现妈呀系统复杂度提升了
一个数量级,也许是复杂了10倍。但是关键时刻,用,还是得用的。
(3)Kafka、 ActiveMQ RabbitMQ、 RocketMQ有什么优缺点?
特性 ActiveMQ RabbitMQ RocketMQ kafka
单机吞吐量万级,比 RocketMQ、 Kafka低一个数量级同 ActiveMQ10万级支撑高
吞吐10万级,高吞吐,一般配合大数据类的系统来进行实时数据计算、日志采集等场
景
topic数里对吞吐里的影响
topic可以达到几百几千的级别吞叶里会有较小幅度
的下降,这是 RocketMQ的一大优势,在同等机器下,可以支撑大里的 topic topic从几十
到几百个时候,吞吐里会大幅度下降,在同等机器下, Kafka尽里保证 topic数里不要过多,
如果要支撑大规模的 topic,需要增加多的机器资源
时效性ms级微秒级,这是 RabbitMQ的一大特点,延迟最低ms级ms级以内
可用性高,基于主从架构实现高可用同 ActiveMQ非常高分布式架构非常高分布
式,一个数据多个副本,少数机器宕机,不会丢失数据,不会导致不可用
消息可靠性有较低的概率丢失数据基本不丢经过参数优化酷,可以做到0丢
失同 RocketMQ
功能支持MQ领域的功能极其完备基于 erlang开发并发能力很强,性能极好,延
时很低MQ功能较为完善,还是分布式的扩展性好功能较为简单,主要支持简单的
MQ功能,在大数据领域的实时计算以及日志采集被大规模使用
中小型公司,技术实力较为一般,技术挑战不是特别高,用RabbitMQ是不错的选择;大
型公司,基础架构研发实力较强,用RocketMQ是很好的选择。如果是大数据领域的实时
计算、日志采集等场景,用 Kafka是业内标的,绝对没问题,社区活跃度很高,绝对不
会黄,何况几乎是全世界这个领或的事实性规范。
二、缓存
(1)缓存的意义
为什么使用缓存?
高性能,高并发
高性能
假设这么个场景,你有个操作,一个请求过来,吭哧你各种乱七八糟操作mysq半天
查出来一个结果,耗时600ms。但是这个结果可能接下来几个小时都不会变了,或者变了
也可以不用立即反馈给用户。那么此时咋办?
缓存啊,折腾600ms查出来的结果,扔缓存里,一个key对应一个 value,下次再有人查,
别走 mysal折腾600ms了,直接从缓存里通过一个key查出来个 value,2ms搞定
性能提升300倍。
就是说对于一些需要复杂操作耗时查出来的结果,且确定后面不怎么变化,但是有很多读请
求,那么直接将查询出来的结果放在缓存中,后面直接读缓存就好。
高并发
mysq这么重的数据库,压根儿设计不是让你玩儿高并发的,虽然也可以玩儿,但是天然支
持不好。mysq单机支撑到2000QPs也开始容易报警了。
所以要是你有个系统,高峰期一秒钟过来的请求有1万,那一个mysq单机绝对会死掉
你这个时候就只能上缓存,把很多数据放缓存,别放myq缓存功能简单说白了就是
key- -value式操作,单机支撑的并发里轻松一秒几万十几万,支撑高并发so eas单机承载
并发是mysq单机的几十倍。
缓存是走内存的,内存天生就是支撑高并发的
(2)用了缓存之后会有什么不良后果?
缓存和数据库双写不一致
缓存雪崩、穿透、击穿
缓存并发竞争
(3) redis和 memcached区别
redis支持复杂的数据结构
redis相比 memcached来说,拥有更多的数据结构,能支持更丰富的数据操作。如果需要
缓存能多支持更复杂的结构和操作, redis会是不错的选择。
redis原生支持集群模式
在 redis33.x版本中,便能支持 cluster模式,而memcached没有原生的集群模式,需要依
靠客户端来实现往集群中分片写入数据。