1、消息中间件的作用
解耦、异步、削峰
耦合的场景:
解耦后的场景
不用MQ的同步高延时请求场景
使用MQ进行异步化之后的接口性能优化
没有有MQ的时候高峰期系统宕机的场景
使用MQ来进行削峰的场景
架构中引入MQ后可能存在的一些问题
如何保证消息中间件的高可用性
2、镜像集群模(rabbitmq的高可用方式)
kafka(纯分布式的mq,如何实现高可用的架构)
采用分布式的副本来实现高可用,各副本之间存在leader和follower,生产者只能往leader中写
如何保证消息不被重复消费?(=如何保证消息消费时的幂等性?)
如何保证消息传输的可靠性?(如何处理发到消息队列中的数据不见了?或数据丢失,以rabbitmq为例)
1、事务机制
2、confirm确认机制
3、消费者处理消息失败(rabbitmq)
4、kafka消息丢失问题
-
消费者丢失,将自动offset改成手动的offset
-
kafka丢失
-
生产者丢失
4、如何保证消息的顺序性
rabbitmq可能存在的顺序错乱问题
解决办法:将有顺序的数据写到同一个queue中
kafka可能存在的顺序错乱问题的解决办法
写入一个partition中的数据一定是有顺序的
多线程时+内存队列进行处理
如何解决 消息队列的延时以及过期失效问题? 消息队列满了以后该怎么处理?有几百万消息持续积压几小时,说说怎么解决?
如果让你设计消息中间件 -
首先这个 mq 得支持可伸缩性吧,就是需要的时候快速扩容,就可以增加吞吐量和容量,那怎么搞?设计个分布式的系统呗,参照一下 kafka的设计理念,broker -> topic -> partition,每个 partition放一个机器,就存一部分数据。如果现在资源不够了,简单啊,给 topic 增加partition,然后做数据迁移,增加机器,不就可以存放更多数据,提供更高的吞吐量了?
-
其次你得考虑一下这个 mq
的数据要不要落地磁盘吧?那肯定要了,落磁盘才能保证别进程挂了数据就丢了。那落磁盘的时候怎么落啊?顺序写,这样就没有磁盘随机读写的寻址开销,磁盘顺序读写的性能是很高的,这就是kafka 的思路。 -
其次你考虑一下你的 mq 的可用性啊?这个事儿,具体参考之前可用性那个环节讲解的 kafka 的高可用保障机制。多副本 -> leader& follower -> broker 挂了重新选举 leader 即可对外服务。
-
能不能支持数据 0 丢失啊?可以的,参考我们之前说的那个 kafka 数据零丢失方案。