消息队列总览
2026/10/11大约 3 分钟
消息队列总览
消息队列(Message Queue, MQ)是分布式系统的「异步总线」:生产者把消息丢进队列就返回,消费者按自己的节奏取走处理。它一举解决三个问题——解耦(上下游不必同步调用)、削峰(洪峰流量先缓冲再匀速消化)、事件驱动(系统间通过事件而非接口协作)。代价是引入了一条新的、可能丢消息、可能重复、可能乱序的链路。
1. 为什么需要 MQ
同步调用的世界很脆弱。下单接口要同时调库存、积分、通知三个服务,任一超时就拖垮整条链路,流量高峰直接把下游打崩。引入 MQ 后:
- 下单只写库 + 发一条「订单已创建」事件,立即返回;
- 积分、通知各自订阅,独立消费,互不阻塞;
- 峰值流量堆在队列里,消费者按自身能力匀速处理——这就是削峰填谷。
代价也随之而来:消息可能重复(网络重试导致)、可能丢失(任一段落没有可靠保证)、可能乱序(多分区/多消费者并发)。这三个是 MQ 的「共性问题」,选任何一款产品都逃不掉,必须在业务层设计对策。
2. 三款主流产品对比
| 维度 | Kafka | RabbitMQ | RocketMQ |
|---|---|---|---|
| 定位 | 分布式流平台 / 日志管道 | 传统消息中间件(AMQP) | 互联网业务消息中间件 |
| 语言/协议 | Scala/Java,自有协议 | Erlang,AMQP 0-9-1 | Java,自有协议 |
| 吞吐量 | 极高(十万级+/秒) | 中等(万级/秒) | 高(十万级/秒) |
| 延迟 | 毫秒级 | 微秒~毫秒级 | 毫秒级 |
| 消息模型 | 分区 + 消费者组(拉) | 交换机路由 + 队列(推/拉) | 队列 + 消费者组(拉) |
| 路由灵活性 | 弱(按 key/分区) | 强(direct/topic/fanout/headers) | 中(Tag 过滤) |
| 顺序消息 | 分区内有序 | 队列内有序 | 支持严格顺序消息 |
| 事务/延时 | 有事务;延时靠外部 | 有发布确认;延时靠插件 | 原生事务消息、延时消息 |
| 消息回溯 | 支持(按 offset 重放) | 消费即出队,不回溯 | 支持(按 offset 回溯) |
| 典型场景 | 日志采集、埋点、流处理、CDC | 业务解耦、任务队列、路由复杂场景 | 电商/交易、订单、支付、削峰 |
3. 选型建议
- 日志、埋点、大数据管道、事件溯源、需要高吞吐与可回溯 → Kafka。它是流处理生态(Flink/Spark)的事实标准。
- 路由规则复杂、需要灵活绑定、消息量中等、要传统 AMQP 语义 → RabbitMQ。交换机模型表达能力最强,管理界面友好。
- 互联网业务消息,需要原生事务消息/延时消息/严格顺序 → RocketMQ。为电商交易场景量身定制,低延迟且支持海量堆积。
现实里也常见组合使用:Kafka 扛日志与数据管道,RocketMQ 或 RabbitMQ 扛核心业务消息,各司其职。
4. 共性问题的通用对策
| 问题 | 通用思路 |
|---|---|
| 重复消费 | 消费端做幂等:唯一业务键去重、状态机、去重表 |
| 消息丢失 | 生产端确认(acks/confirm)、broker 持久化与副本、消费端手动 ack |
| 消息乱序 | 需要顺序的业务把同一业务键路由到同一分区/队列;否则在消费端按序重组 |
| 消息堆积 | 扩分区/扩消费者、排查消费端慢逻辑、临时降级 |
5. 本站文档
- Kafka 详解:分区副本 ISR、日志存储、生产者 acks、消费者组与 rebalance、幂等与事务。
- RabbitMQ 详解:交换机类型、队列与 ack、死信、TTL、镜像队列与 quorum 队列。
- RocketMQ 详解:NameServer/Broker、CommitLog、顺序消息、事务消息、延迟消息、刷盘与主从。