RabbmitMQ-Publish/Subscribe
之前的学习中,我们了解的工作队列实现的是:一个消息只发送到一个消费者。
现在我们来学习一下新模式:发布/订阅模式
之前我们在原理中介绍了exchange,但好像并没有使用。而是直接往队列里发消息和取消息。现在我们使用rabbitmq的消息模型,利用交换机来转发消息。
首先我们来了解一下exchange的四种类型:fanout、direct、topic、headers
fanout:

1、消息与队列匹配规则:该类型交换机会将收到的消息广播给所有与之绑定的队列
2、该情况下,生产者只关系消息发送到哪个交换机,由交换机决定消息发送到哪些队列。而消费者只关系订阅哪个队列
direct:

1、消息分发规则:消息会被推送至绑定键(binding key)和消息发布附带的路由键(routing key)完全匹配的消息
2、图示说明:消息1附带路由键“error”、与绑定键“error”匹配,而队列Q4、Q5与交换机X间都存在绑定键“error”所以消息1被分发到Q4、Q5;消息2附带路由键“info”,而队列Q4与交换机间存在绑定建“info”,所以消息2被分发到队列Q4。
3、分发到队列的消息不再带有发送者的任何信息,如果消息实体里包含了发送者的信息,那么消费者可以获取发送者信息
topic:

1、消息分发规则:一个附带特殊的路由键(routing key)会被转发到绑定键(binding key)与之匹配的队列中
2、routing key与binding key匹配规则: routing key必须是由点隔开的一系列的标识符组成。标识符可以是任何东西,但一般都与消息的某些特效有关。如:"stock.usd.nyse","nyse.vmw","quick.orange.rabbit"。上限为255字节。 绑定键与选择键形式一样。 两种特殊情况:*匹配一个标识符、#匹配0个或多个标识符
3、图示说明: 消息1附带路由键“fast.orange.*”与绑定键“#”、“*.orange.*”匹配,所以消息1被分发给队列Q6、Q7;消息2附带路由键“lazy.orange.a.b”与绑定键“#”、“lazy.#”匹配,所以消息2被分发给队列Q6、Q8。
headers:

1、消息分发规则: headers类型的交换机发消息不依赖routing key。而是使用发消息时basicProperties对象中的headers匹配。headers是一个键值对类型。发送者发消息时将这些键值对放在basicProperties对象的headers字段中。队列绑定交换机时绑定一些键值对。两者匹配时。队列就可以收到消息。
匹配模式有两种:
在队列绑定到交换机时用x-match来指定,all代表定义的多个键值对都要满足,any代表只要满足一个就可以。fanout,direct,topic中的routing 可以需要字符串,而headers没有这个要求。键值对可以是任何类型。
2、图示说明: 消息1附带的键值对与Q9绑定键值对的color匹配、speed不匹配,但是Q9的x-match设置为any,因此只要有一项匹配消息1就可以被分发到Q9。消息1与Q10完全匹配,消息2与Q10部分匹配,由于Q10的x-match设置为all,所以只能接受到消息1。
案例:创建一个简单的日志系统,有两个程序组成:一个输出日志消息,一个接收并打印日志消息
在该系统中,每一个cusumer都会接到所有消息,其中一个cusumer直接保存消息到磁盘,另一个cusumer输出消息
在该案例中,我们使用fanout类型的exchange,通过 channel.exchangeDeclare("logs,"fanout")来设置参数
在rabbitmq中,默认的exchange的名字是空字符串。
在coding之前我们还要了解一下些小知识:
临时队列:
当我们指定了特定名字的队列时,我们要让消费者指向同一个队列。当生产者消费者共用一个队列时。队列名字非常重要。 对于本案例的日志系统而言,我们想让每个消费者都接到所有的日志消息。而不是其中一部分。我们关心的是当前广播的消息而不是之前的。所以我们要做两件事情满足我们的要求:
1、我们连接rabbitmq服务时,需要一个新鲜的空的队列。我们自定义随机名,更好的是让rabbitmq服务器为我们的队列随机起名
2、当我们关闭消费者时,队列应该自动删除
如何创建队列名呢?
String queueName = channel.queueDeclare().getQueue();
这样可以获取随机的队列名 调用无参的queueDeclare方法时,就创建一个非持久、独特的会自动删除的队列
绑定:
我们创建了一个fanout类型的exchange和一个队列。我们需要告诉exchange发送消息到我们的队列。exchange与队列之间的关系称为绑定(binding)。
channel.queueBind(queueName,"logs",""); 这样我们就将创建的队列和exchange建立了关系。
exchange会将消息发送到这个队列 rabbitmqctl list_binding 查看所有已经存在的绑定关系
Coding一下,你就知道
producer:

cusumer: 
在这个模式下:
对于producer而言,我们将消息发送给logs交换机,而不是无名的交换机。发消息时我们提供一个路由键routing key。但它的值会被fanout类型的交换机忽略。
如果路由器还没有绑定队列,这些发送给路由器的消息将会丢失。但这对我们无所谓,如果还没有cusumer监听,我们可以安全地丢弃这些消息。
RabbmitMQ-Publish/Subscribe的更多相关文章
- 使用Guava EventBus构建publish/subscribe系统
Google的Guava类库提供了EventBus,用于提供一套组件内publish/subscribe的解决方案.事件总线EventBus,用于管理事件的注册和分发.在系统中,Subscribers ...
- 【RabbitMQ】Publish/Subscribe
Publish/Subscribe 在上一节我们创建了一个work queue.背后的设想为每个任务被分发给明确的消费者.这节内容我们将做一些完全不同的事情 -- 我们将发送一条消息给多个消费者.这种 ...
- publish/subscribe
Pub/Sub功能 Pub/Sub功能(means Publish, Subscribe)即发布及订阅功能.基于事件的系统中,Pub/Sub是目前广泛使用的通信模型,它采用事件作为基本的通信机制,提供 ...
- Mina、Netty、Twisted一起学(七):发布/订阅(Publish/Subscribe)
消息传递有很多种方式,请求/响应(Request/Reply)是最常用的.在前面的博文的例子中,很多都是采用请求/响应的方式,当服务器接收到消息后,会立即write回写一条消息到客户端.HTTP协议也 ...
- RabbitMQ(三) -- Publish/Subscribe
RabbitMQ(三) -- Publish/Subscribe `rabbitmq`支持一对多的模式,一般称为发布/订阅.也就是说,生产者产生一条消息后,`rabbitmq`会把该消息分发给所有的消 ...
- ZeroMQ之Publish/Subscribe (Java)
前面的文章介绍了比较简单的Request/Subscribe模式, 这篇文章介绍更为经典的Publish/Subscribe通信模式用来ZeroMQ的实现,其通信方式如下图: 客户端(subscrib ...
- RabbitMQ学习总结 第四篇:发布/订阅 Publish/Subscribe
目录 RabbitMQ学习总结 第一篇:理论篇 RabbitMQ学习总结 第二篇:快速入门HelloWorld RabbitMQ学习总结 第三篇:工作队列Work Queue RabbitMQ学习总结 ...
- (转)RabbitMQ消息队列(四):分发到多Consumer(Publish/Subscribe)
上篇文章中,我们把每个Message都是deliver到某个Consumer.在这篇文章中,我们将会将同一个Message deliver到多个Consumer中.这个模式也被成为 "pub ...
- 【转】Difference between Point-To-Point and Publish/Subscribe JMS Messaging Models
Difference between Point-To-Point and Publish/Subscribe JMS Messaging Models Point-to-Point (PTP) ...
- javascript设计模式——Publish/Subscribe
推荐阅读http://dev.housetrip.com/2014/09/15/decoupling-javascript-apps-using-pub-sub-pattern/ 我们先引出问题的所在 ...
随机推荐
- Angular基础(二) 组件的使用
一.简单操作 a) 使用Angular CLI可以快速创建项目框架,先运行 $ npm install –g @angular/cli@1.0.0安装CLI,为CLI的位置设置环境变量,然后就可以 ...
- MVC与单元测试实践之健身网站(四)-动作管理
网站后台负责进行动作的管理,包括动作名称.介绍.训练要点.配图等内容,以便前台能够使用这些内容.在上一篇< Fit项目图片上传和云存储的调通>中已经准备好了这里涉及到的主要技术难点,现在就 ...
- (后端)出现org.hibernate.NonUniqueResultException的原因即解决办法
百度出来的资料解决问题: 一个问题,事务处理完毕以后页面没有刷新.刚开始以为是前台js的问题,后来检查js没有任何问题,跟踪到后台发现后台报错了,错误信息如下:org.hibernate.NonUni ...
- ubuntu18.04突然无法上网解决方法
sudo service network-manager stop sudo rm /var/lib/NetworkManager/NetworkManager.state sudo service ...
- Ubuntu 17.10 环境初始化
输入法(中文) sogoupinyin fcitx-table-wubi 输入法快捷键 Ctrl + Space(两个间切换), Ctrl + Shift(多个间切换), Shift中英切换 与Win ...
- 【第一章】zabbix3.4监控WindowsCPU使用率磁盘IO磁盘事件日志监控阈值邮件报警详细配置
Windows安装zabbix-agent 监控Windows-CPU使用率 监控Windows-磁盘IO性能监控 监控Windows/Linux-磁盘触发器阈值更改 监控Windows-网卡自动发现 ...
- Linux初学 - Centos7忘记root密码的解决办法
开机进入启动界面后,要按照屏幕的下方的操作提示迅速按下“e”键. 按下“e”键后即来到启动文件界面,这时按键盘上面的方向键“下”,一直到文件底部,在"LANG=zh_cn.UTF-8&quo ...
- golang xorm框架的使用
1.创建engine engine, err := xorm.NewEngine(driverName, dataSourceName) 上述代码创建了一个数据库引擎,可以在一个程序中创建多个engi ...
- MongoDB基础教程系列--目录结构
最近对 MongoDB 产生兴趣,在网上找的大部分都是 2.X 版本,由于 2.X 与 3.X 差别还是很大的,所以自己参考官网,写了本系列.MongoDB 的知识还是很多的,本系列会持续更新,本文作 ...
- 2017-2018-2 20155314《网络对抗技术》Exp3 免杀原理与实践
2017-2018-2 20155314<网络对抗技术>Exp3 免杀原理与实践 目录 实验要求 实验环境 预备知识 实验步骤 1 免杀效果实测 1.1 恶意代码生成工具 1.2 免杀效果 ...