【RabbitMQ】 RabbitMQ Overview
RabbitMQ Overview
Concept
不同协议间的区别,其中AMQP0-9-1是RabbitMQ的默认协议,下文都是基于此协议进行描述。
协议 | 协议类型 | 设计特点与目标 | 核心消息语义 | 典型应用场景 |
---|---|---|---|---|
AMQP 0-9-1 | 二进制协议 | RabbitMQ的核心协议,提供强大的消息传递语义,支持可靠排队、灵活路由、事务等,功能丰富 | 点对点、发布/订阅、路由(通过不同类型的交换机实现) | 企业级应用、订单处理、支付回调等对可靠性要求高的场景 |
MQTT | 二进制协议 | 轻量级,专为低带宽、高延迟网络和资源受限的物联网设备设计 | 发布/订阅(主题模式),提供多种服务质量等级 | 物联网(IoT)、移动应用、小型设备通信 |
STOMP | 文本协议 | 简单易用,基于文本,易于手动实现和调试(如通过Telnet) | 简单的消息帧,语义定义较少,依赖Broker实现队列和主题的映射 | Web应用程序、移动应用程序间的简单消息传递,结合WebSockets用于浏览器 |
AMQP 1.0 | 二进制协议 | 与AMQP 0-9-1不兼容,是功能不同的独立协议,协议本身更复杂 | 语义要求较少,更通用,易于在现有Broker上实现支持 | 需要与支持AMQP 1.0的其他系统(如IBM MQ)进行互操作的场景 |
HTTP | 文本协议(非消息协议) | 利用HTTP API进行消息传输,通常不保证可靠交付 | 简单的请求/响应,同步通信 | 管理诊断、低容量且对可靠性要求不高的消息传递 |
AMQP-0-9-1
AMQP 0-9-1 (Advanced Message Queuing Protocol) is a messaging protocol that enables conforming client applications to communicate with conforming messaging middleware brokers.
消息发布到交换机,交换机通常比作邮局或邮箱。然后,交换机使用称为绑定的规则将消息副本分发到队列。然后,代理将消息传递给订阅队列的消费者,或者消费者按需从队列中获取/拉取消息。
RabbitMQ组成
- Broker:消息队列服务进程。此进程包括两个部分:Exchange和Queue。
- Exchange:消息队列交换机。按一定的规则将消息路由转发到某个队列。
- Queue:消息队列,存储消息的队列。
- Producer:消息生产者。生产方客户端将消息同交换机路由发送到队列中。
- Consumer:消息消费者。消费队列中存储的消息。
如上图所示,RabbitMQ 由 Producer、Broker、Consumer 三个大模块组成。生产者将数据发送到 Broker,Broker 接收到数据后,将数据存储到对应的 Queue 里面,消费者从不同的 Queue 消费数据。
那么除了 Producer、Broker、Queue、Consumer、ACK 这几个消息队列的基本概念外,它还有 Exchange、Bind、Route 这几个独有的概念。下面来简单解释下。
Exchange 称为交换器,它是一个逻辑上的概念,用来做分发,本身不存储数据。流程上生产者先将消息发送到 Exchange,而不是发送到数据的实际存储单元 Queue 里面。
然后 Exchange 会根据一定的规则将数据分发到实际的 Queue 里面存储。这个分发过程就是 Route(路由),设置路由规则的过程就是 Bind(绑定)。
即 Exchange 会接收客户端发送过来的 route_key,然后根据不同的路由规则,将数据发送到不同的 Queue 里面。
这里需要注意的是,在 RabbitMQ 中是没有 Topic 这个用来组织分区的逻辑概念的。RabbitMQ 中的 Topic 是指 Topic 路由模式,是一种路由模式,和消息队列中的 Topic 意义是完全不同的。
那为什么 RabbitMQ 会有 Exchange、Bind、Route 这些独有的概念呢?
在我看来,主要和当时业界的架构设计思想以及主导设计 AMQP 协议的公司背景有关。当时的设计思路是:希望发消息跟写信的流程一样,可以有一个集中的分发点(邮局),通过填写好地址信息,最终将信投递到目的地。这个集中分发点(邮局)就是 Exchange,地址信息就是 Route,填写地址信息的操作就是 Bind,目的地是 Queue。
Exchanges
- Fanout: covered in tutorial 3
- Topic: covered in tutorial 5
- Direct: covered in tutorial 4
- Default direct exchange: a built-in direct exchange with special characteristics
- Local Random
- JMS Topic
- Consistent Hashing exchange
- Random exchange
- Recent history exchange
- Headers
RabbitMQ中的消息模式
Sample - hello world
RabbitMQ tutorial - "Hello World!" | RabbitMQ
一个生产者,一个消费者,一个队列,采用默认交换机。可以理解为生产者P发送消息到队列Q,一个消费者C接收。
Work Queue
RabbitMQ tutorial - Work Queues | RabbitMQ
一个生产者,多个消费者,一个队列,采用默认交换机。可以理解为生产者P发送消息到队列Q,可以由多个消费者C1、C2进行接收。
发布/订阅模式(fanout)
RabbitMQ tutorial - Publish/Subscribe | RabbitMQ
一个生产者、一个 fanout 类型的交换机、多个队列、多个消费者。一个生产者发送的消息会被多个消费者获取。其中 fanout 类型就是发布订阅模式,只有订阅该生产者的消费者会收到消息。
路由模式(direct)
RabbitMQ tutorial - Routing | RabbitMQ
一个生产者,一个 direct 类型的交换机,多个队列,交换机与队列之间通过 routing-key 进行关联绑定,多个消费者。生产者发送消息到交换机并且要指定routing-key,然后消息根据这交换机与队列之间的 routing-key 绑定规则进行路由被指定消费者消费。
发布订阅模式是无条件将所有消息分发给所有消费者队列。
路由模式则是交换机根据Routing Key有条件的将数据筛选后发给消费者队列。
主题模式(topic)
RabbitMQ tutorial - Topics | RabbitMQ
一个生产者,一个 topic 类型的交换机,多个队列,交换机与队列之间通过 routing-key 进行关联绑定,多个消费者。生产者发送消息到交换机并且要指定 routing-key,然后消息根据这交换机与队列之间的 routing-key 绑定规则进行路由被指定消费者消费。与路由模式不同是 routing-key 有指定的队则,可以更加的通用,满足更过的场景。routing-key 的规则如下:
#
:匹配一个或者多个词,例如lazy.#
可以匹配 lazy.xxx 或者 lazy.xxx.xxx*
:只能匹配一个词,例如lazy.*
只能匹配 lazy.xxx