✅如果让你实现消息队列,会考虑哪些问题?

典型回答

这是一个比较常见的场景题,让实现某个中间件,其实主要就是拆解,基于自己对已有的消息中间件,如Kafka、RocketMQ等的理解,进行回答这个问题。

主要可以从以下几个方面来回答这个问题:

基本架构和功能

当设计一个消息队列的时候,需要考虑它的基本架构及功能,这是首先需要考虑的。

  • 生产者、消费者、Broker:生产者负责发送消息,消费者负责接收消息,Broker作为服务端,处理消息的存储、备份、删除和消费关系维护。
  • 主题和分区:主题(Topic)是消息分类的标识,而分区是主题的物理分割,有助于提高消息队列的吞吐量。

比如我们知道的Kafka、RocketMQ、RabbitMQ等等,都有各自的架构设计方案

✅Kafka的架构是怎么样的?

✅RocketMQ的架构是怎么样的?

✅rabbitMQ的整体架构是怎么样的?

基本功能

  • 消息存储方式:消息队列需要将消息存储在某种媒介中,一般采用内存或者磁盘存储。在内存存储的情况下,可以快速的读写消息,但是可能会丢失消息,因为内存中的消息没有持久化。而采用磁盘存储,可以持久化消息,但是读写速度相对慢一些。
  • 消息传递协议:消息队列需要定义消息传递的协议,包括消息格式、消息队列的地址等信息。我们可以使用成熟的RPC框架(如Dubbo或Thrift)实现生产者和消费者与Broker之间的通信。
  • 消息的持久化和确认机制:在消息队列中,需要实现消息的持久化和确认机制,确保消息不会丢失或重复消费。一般的做法是将消息存储在磁盘中,并在消费者确认消费完成后再删除消息。

  • 消息的分发方式:消息队列需要实现消息的分发方式,包括点对点和广播两种方式。在点对点方式下,每个消费者只会接收到自己订阅的消息;在广播方式下,每个消费者都会接收到所有的消息。

✅RocketMQ怎么实现消息分发的?

  • 消息的传递方式:在消息队列中,有多种消息的传递方式,如轮询、长连接,还有长轮询。一般都是支持推拉结合的方式。或者基于拉实现推的机制。

✅消息队列使用拉模式好还是推模式好?为什么?

消息的可靠性保证

  1. 消息队列的容错性和可用性:消息队列需要实现高可用和容错机制,以确保消息的可靠传输。一般的做法是采用主从复制、集群模式或者分布式架构来实现。

✅Kafka如何保证消息不丢失?

✅RocketMQ如何保证消息不丢失?

✅RabbitMQ如何保证消息不丢

高性能设计

高性能这部分可以参考kafka,引入一些批量操作、顺序写入、零拷贝等技术。

✅Kafka 为什么这么快?

功能扩展

除了一些基本的消息发送、投递以外,还需要考虑一些具体的业务场景。比如实现事务消息、实现延迟消息、实现顺序消息等等。

  • 顺序消息

✅Kafka如何实现顺序消费?

✅RocketMQ如何保证消息的顺序性?

  • 延迟消息

✅rabbitMQ如何实现延迟消息?

✅RocketMQ如何实现延时消息?

  • 事务消息

✅RocketMQ的事务消息是如何实现的?

还需要考虑一些MQ使用时候可能会出现的消息堆积、消息重复消费等问题。

  • 重复消费

✅Kafka怎么保证消费只消费一次的?

✅RabbitMQ如何防止重复消费

  • 消息堆积

✅RocketMQ消息堆积了怎么解决?

还有一些其他的问题,比如重平衡的问题,集群数据同步的问题等。

原文: https://www.yuque.com/hollis666/xkm7k3/zge9wo