RabbitMQ工作模式 - 路由模式(Direct 模式) --- 2022-04-03

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了RabbitMQ工作模式 - 路由模式(Direct 模式) --- 2022-04-03相关的知识,希望对你有一定的参考价值。

参考技术A RabbitMQ路由模式大体上跟发布订阅模式一样,区别在于发布订阅模式将消息转发给所有绑定的队列,而路由模式将消息转发给那个队列是根据路由匹配情况决定的。

从具体编码角度看,路由模式跟发布订阅模式的区别就是使用的交换机(Exchange)类型不一样,路由模式使用的是Direct类型

说明:

例如上图:
队列Q1的routing key=orange,队列Q2的routing key=black和green,发送消息的时候,如果消息的routing key = orange,则转发至Q1队列,消息的routing key = black和green则转发至Q2队列。

路由模式是在发布订阅模式的基础上进行了扩展,因此应用场景跟发布订阅模式类似,区别是允许设置消息订阅的条件。

例如:
某电商网站,有华东、华南、华北、西南四个仓库,每个仓库部署了一套仓储系统,用户购物下单后,由最近的仓库负责发货。

用户下单后产生下单消息,我们希望将消息转发至对应的地区的仓储系统处理,可以使用路由模式。

四个仓储系统的发货队列绑定的routing key如下:

用户下单后计算用户地址属于哪个地区,算出routing key,然后发送下单消息的时候携带routing key即可,RabbitMQ direct交换机会转发至对应的队列。

RabbitMQ

1 RabbitMQ工作原理

2 RabbitMQ六种工作模式

2.1 simple简单模式

一个队列中,一条消息只能被一个消费者消费;

2.2 work工作模式

一个生产者,多个消费者,每个消费者获取到的消息唯一;

2.3 Router路由模式

消息需要制定direct类型的exchange和RoutingKey, 将消息发送到routingkey全匹配的队列;

2.4 Topic主题模式

消息需要制定topic类型的exchange和RoutingKey, 将消息发送到routingkey模糊匹配的队列;

2.5 Fanout发布订阅模式

消息需要制定fanout类型的exchange, 消息发送到该交换机的所有队列中;

2.6 Header模式

消息需要制定header类型的exchange,根据发送的消息内容中的headers属性进行匹配。

3 RabbitMQ部署方案

3.1 单节点模式

最简单的情况,非集群模式,节点挂了,消息就不能用了。业务可能瘫痪,只能等待。

3.2 普通模式

默认的集群模式,某个节点挂了,该节点上的消息不能用,有影响的业务瘫痪,只能等待节点恢复重启可用(必须持久化消息情况下)。

3.3 镜像模式

把需要的队列做成镜像队列,存在于多个节点,属于RabbitMQ的HA方案;
为什么设置镜像模式集群,因为队列的内容仅仅存在某一个节点上面,不会存在所有节点上面,所有节点仅仅存放消息结构和元数据。

如果想解决上面途中问题,保证消息不丢失,需要采用HA 镜像模式队列。
下面介绍下三种HA策略模式
1)同步至所有的;
2)同步最多N个机器;
3)只同步至符合指定名称的nodes。

缺陷:所有的读写都是在master上进行,从节点只是备份,最终会路由到master进行处理。

4 RabbitMQ如何保证消息不丢失

4.1 丢失消息的3种场景

4.2 解决方案

  1. 发送消息开启confirm模式,MQ收到消息后异步通知生产者,消息发送成功。
  2. 消息持久化:
    • .Exchange 设置持久化:durable = true
    • Queue 设置持久化:durable = true
    • Message持久化发送:发送消息设置发送模式deliveryMode=2,代表持久化消息。
  3. 镜像集群部署模式。
  4. 手动ACK:使用Message acknowledgment 机制,就是消费端消费完成要通知服务端,服务端才把消息从内存删除。

这样就解决了,即使一个消费者出了问题,没有同步消息给服务端,还有其他的消费端去消费,保证了消息不丢。

5 如何保证顺序消费

  • 设置每次只取一条消息:perfach_count=1
  • 设置消费者为1:consumer=1,max_consumer=1
  • 设置首次声明它的连接可见:exclusive = true
    • 针对连接可见,只要是当前connection下的信道都可以访问
    • 一旦该队列被声明,其他连接无法声明相同名称的排他队列。
    • 队列即使显示声明为durable,连接断开时(注意不是信道断开)也会被自动删除。

6 如何提高队列的消费速度

降低生产速度:往往跟业务相关。
提高消费速度:批量操作,减少重复查询,SQL优化。
支持并发消费:设置多个并发消费者或者增加服务节点。
拆分任务队列:大任务,拆分几个小任务并发消费。

7 和kafaka的区别

  • 语言不同:RabbitMQ是erlanng语言开发,kafka是cala语言开发。
  • 结构不同:RabbitMQ采用AMQP(Advanced Message Queuing Protocol,高级消息队列协议)是一个进程间传递异步消息的网络协议,kafka采用mq结构:broker 有part 分区的概念。
  • Broker与Consume交互方式不同:RabbitMQ 采用push的方式,kafka采用pull的方式。
  • 在集群负载均衡方面:rabbitMQ的负载均衡需要单独的loadbalancer进行支持,kafka采用zookeeper对集群中的broker、consumer进行管理。
  • 使用场景:rabbitMQ支持对消息的可靠的传递,支持事务,不支持批量的操作;基于存储的可靠性的要求存储可以采用内存或者硬盘,金融场景中经常使用。kafka具有高的吞吐量,内部采用消息的批量处理,zero-copy机制,数据的存储和获取是本地磁盘顺序批量操作,具有O(1)的复杂度(与分区上的存储大小无关),消息处理的效率很高。(大数据)

8 延迟队列的实现

8.1 采用死信队列

  • 相同延迟时间的任务放一个队列。不同延迟时间的分开多个任务队列。
  • 不同延迟时间的任务都放一个队列。有可能导致到时间了还没消费的情况。

8.2 采用插件的方式

收到消息后并未立即把消息投递到目标队列,而是存储在一个mnesia(分布式数据库中)中,随后检查消息延迟时间,到达可投递时间,将其通过x-delayed-type类型标记的交换机投递到目标队列。

以上是关于RabbitMQ工作模式 - 路由模式(Direct 模式) --- 2022-04-03的主要内容,如果未能解决你的问题,请参考以下文章

RabbitMQ学习笔记

万字长文图文详解Springboot集成RabbitMQ(直连模式,工作队列模式,发布订阅模式,路由模式,通配符模式)

RabbitMQ六种队列模式-工作队列模式

RabbitMQ五种工作模式学习总结

RabbitMQ

RabbitMQ六种队列模式-简单队列模式