RabbitMQ中的Channel和Exchange详解
作者:weixin_44463587
channel
有了TCP连接后,还需要channel的原因如下:
- 创建和销毁TCP连接很耗时;
- 打开太多TCP连接,耗操作系统资源,并发量大到一定程度,系统的吞吐量会降低;
- 使用一个connection多channel的方式,可以提升连接的利用率。
因此采用多个channel多路复用一个TCP连接的方式才比较合理
exchange(交换机)
生产者发消息发往交换机,交换机会自己投递消息到绑定的queue队列
1.exchange根据什么规则把消息投递到哪些queue中?
exchange有4种类型
- direct: 对routing_key进行严格匹配,当消息来到的时候,只有exchange与某queue绑定的routing_key完全匹配才将消息投递到该queue
- topic: 对routing_key进行通配符模糊匹配,满足条件的queue都能收到消息,这里的routing_key以"."分隔,*匹配一个单词,#匹配多个单词,如果同一个queue满足多个条件不会被投递多次
如果消息的routingkey是quick.orange.rabbit,那么Q1 Q2都会收到这条消息。
如果消息的routingkey是quick.orange.fox,那么Q1会收到这条消息
- headers: 根据消息体内的headers属性匹配,绑定的时候可以制定键值对。不依赖routing_key匹配。
大致逻辑与direct差不多,只不过不是用的routing_key来匹配
- fanout: 转发消息到所有绑定队列,不依赖routing_key匹配
在不需要路由的时候,一般是使用的这个类型的exchange。
- 发布订阅:两个queue绑定到同一个exchange上,那么同一个消息被发送到exchange后,exchange会把这个消息发给绑定的所有队列,两个消费者,一人消费一个队列,这就在这两个消费者之间达到了发布订阅的效果
- 竞争消费:两个消费者消费同一个队列,这就达到了这两个消费者之间的竞争消费效果。
注意,实际上在写代码的时候不显示指定exchange的数据是发送到一个默认的exchange上的。
2.exchange持久化怎么搞?
如果不设置持久化,broker挂了,再重启,这个exchange就不存在了。
在客户端声明exchange的时候有个入参来控制是否持久化
而autoDelete则是,当没有queue绑定的时候是否自动删除这个exchange
3.生产者ACK机制?
事务或者confirm机制:
rabbitmq生产者确保消息一定送达
这个需要借助Server和MQ的交互实现(tx-select/commit, ok/fail)
4.投递方法
basicPublish中的mandatory和immediate mandatory
当mandatory标志位设置为true时如果exchange根据自身类型和消息routeKey无法找到一个符合条件的queue,那么会调用basic.return方法将消息返回给生产者
(Basic.Return + Content-Header + Content-Body);
当mandatory设置为false时,出现上述情形broker会直接将消息扔掉。
immediate 当immediate标志位设置为true时,如果exchange在将消息路由到queue(s)时发现对于的queue上没有消费者,那么这条消息不会放入队列中。
当与消息routeKey关联的所有queue(一个或者多个)都没有消费者时,该消息会通过basic.return方法返还给生产者。
换句话说,无法找到一个消费者时,消息返还给生产者
到此这篇关于RabbitMQ中的Channel和Exchange详解的文章就介绍到这了,更多相关RabbitMQ的Channel和Exchange内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!