RabbitMQ学习笔记(四) Routing
新的场景
在我们学习了RabbitMQ的发布与订阅之后,我们很容易就可以完成一个简单的消息群发器。
使用这个消息群发器,所有的消费者程序实例都会接收到相同的消息信息,从而实现广播的效果。
但是这种广播是一种无意识的广播,即使消息是有分类的,消费者程序也不能自己决定关注的消息类型,只能被动的接收所有的消息,这就导致消费者程序收到许多无用的消息。
如果想要消费者程序自主决定关注的消息类型,我们可以使用RabbitMQ的Routing机制。
Binding
之前学习RabbitMQ的发布与订阅,我们使用如下代码将消息队列和Exchange进行绑定。
channel.QueueBind(queue: queueName, exchange: "broadcast", routingKey: "");
其中有一个参数是routingKey, 我们将它设置为空。
对于fanout类型的Exchange, 在绑定消息队列和Exchange的时候,会自动忽略routingKey。
但是Direct类型的Exchange使用这个参数可以帮助我们对消息进行的分类,这里我们可以简单的认为routingKey就是一种消息类型
Direct Exchange
Direct的路由算法很简单,它会将消息发送到与Direct Exchange绑定并拥有指定routingKey的消息队列中。

一个消息队列与一个Direct Exchange绑定的时候,可以通过多次绑定,拥有多个routingKey。
同理,一个routingKey也可以被多个消息队列拥有。
例:
channel.QueueBind(queue: queueName, exchange: "broadcast", routingKey: "key1"); channel.QueueBind(queue: queueName, exchange: "broadcast", routingKey: "key2");

在发布与订阅中,我们使用生产者程序向Fanout Exchange发送消息的时候,编写了如下代码
channel.BasicPublish(exchange: "broadcast", routingKey: "", basicProperties: null, body: body );
其中routingKey为空, 因为Fanout Exchange并不关心routingKey。
现在我们使用Direct Exchange, 我们需要指定消息类型routingKey。当Direct Exchnage接收到这条消息之后,它查找和他绑定的所有消息队列,如果消息队列拥有这个routingKey,Direct Exchange就会将这条消息传输给它, 这样监听该消息队列的消费者程序就可以接收到这条消息。
修改代码
Send
- Send可以发送3种类型的消息, game, sport, music
- 发送消息时必须指定消息的类型
static string[] availableTypes = { "game", "music", "sport" };
static void Main(string[] args)
{
if (args == null || args.Length == 0)
{
Console.WriteLine("This command line should be like 'dotnet run [message type] [message].'");
Environment.Exit(1);
}
var messageType = args[0];
if (!availableTypes.Contains(messageType))
{
Console.WriteLine("Available message type can be 'game','music','sport'.");
Environment.Exit(1);
}
var factory = new ConnectionFactory()
{
HostName = "localhost"
};
using (var connection = factory.CreateConnection())
{
using (var channel = connection.CreateModel())
{
channel.ExchangeDeclare("broadcast", "direct");
string message = $"{args[0]} news: {args[1]}";
var body = Encoding.UTF8.GetBytes(message);
channel.BasicPublish(exchange: "broadcast",
routingKey: messageType,
basicProperties: null,
body: body
);
Console.WriteLine("[x] Sent {0}", message);
}
}
}
Receive
- Receive可以接收3种类型的消息, game, sport, music
- 程序启动时指定接收的消息类型
static string[] availableTypes = { "game", "music", "sport" };
static void Main(string[] args)
{
if (args == null || args.Length == 0)
{
Console.WriteLine("This command line should be like 'dotnet run [message type 1] [message type 2] [message type 3].'");
Environment.Exit(1);
}
foreach (var type in args)
{
if (!availableTypes.Contains(type))
{
Console.WriteLine("Available message type can be 'game','music','sport'.");
Environment.Exit(1);
}
}
var factory = new ConnectionFactory() { HostName = "localhost" };
using (var connection = factory.CreateConnection())
{
using (var channel = connection.CreateModel())
{
channel.ExchangeDeclare("broadcast", "direct");
var queueName = channel.QueueDeclare().QueueName;
foreach (var type in args)
{
channel.QueueBind(queue: queueName, exchange: "broadcast", routingKey: type);
}
var consumer = new EventingBasicConsumer(channel);
consumer.Received += (model, ea) =>
{
var body = ea.Body;
var message = Encoding.UTF8.GetString(body);
Console.WriteLine("[x] Received {0}", message);
};
channel.BasicConsume(queue: queueName, autoAck: true, consumer: consumer);
Console.Read();
}
}
}
最终效果
启动1个Send, 2个Receive。
一个Receive关注game, music类型的消息。
一个Receive关注sport, game类型的消息。

RabbitMQ学习笔记(四) Routing的更多相关文章
- rabbitMQ学习笔记(四) 发布/订阅消息
前面都是一条消息只会被一个消费者处理. 如果要每个消费者都处理同一个消息,rabbitMq也提供了相应的方法. 在以前的程序中,不管是生产者端还是消费者端都必须知道一个指定的QueueName才能发送 ...
- RabbitMQ学习笔记四:RabbitMQ命令(附疑难问题解决)
本来今天是想做RabbitMQ之优先级队列的,但是,在RabbitMQ Server创建queue时,增加优先级的最大值,头脑发热写了9999999,导致电脑内存直接飙到100%,只能重启电脑,并卸载 ...
- RabbitMQ学习笔记五:RabbitMQ之优先级消息队列
RabbitMQ优先级队列注意点: 1.只有当消费者不足,不能及时进行消费的情况下,优先级队列才会生效 2.RabbitMQ3.5以后才支持优先级队列 代码在博客:RabbitMQ学习笔记三:Java ...
- RabbitMQ学习笔记(五) Topic
更多的问题 Direct Exchange帮助我们解决了分类发布与订阅消息的问题,但是Direct Exchange的问题是,它所使用的routingKey是一个简单字符串,这决定了它只能按照一个条件 ...
- 官网英文版学习——RabbitMQ学习笔记(一)认识RabbitMQ
鉴于目前中文的RabbitMQ教程很缺,本博主虽然买了一本rabbitMQ的书,遗憾的是该书的代码用的不是java语言,看起来也有些不爽,且网友们不同人学习所写不同,本博主看的有些地方不太理想,为此本 ...
- openresty 学习笔记四:连接mysql和进行相关操作
openresty 学习笔记四:连接mysql和进行相关操作 毕竟redis是作为缓存,供程序的快速读写,虽然reidis也可以做持久化保存,但还是需要一个做数据存储的数据库.比如首次查询数据在red ...
- C#可扩展编程之MEF学习笔记(四):见证奇迹的时刻
前面三篇讲了MEF的基础和基本到导入导出方法,下面就是见证MEF真正魅力所在的时刻.如果没有看过前面的文章,请到我的博客首页查看. 前面我们都是在一个项目中写了一个类来测试的,但实际开发中,我们往往要 ...
- IOS学习笔记(四)之UITextField和UITextView控件学习
IOS学习笔记(四)之UITextField和UITextView控件学习(博客地址:http://blog.csdn.net/developer_jiangqq) Author:hmjiangqq ...
- java之jvm学习笔记四(安全管理器)
java之jvm学习笔记四(安全管理器) 前面已经简述了java的安全模型的两个组成部分(类装载器,class文件校验器),接下来学习的是java安全模型的另外一个重要组成部分安全管理器. 安全管理器 ...
- Learning ROS for Robotics Programming Second Edition学习笔记(四) indigo devices
中文译著已经出版,详情请参考:http://blog.csdn.net/ZhangRelay/article/category/6506865 Learning ROS for Robotics Pr ...
随机推荐
- maya cmds pymel selectType() 选择类型切换
maya cmds pymel selectType() 选择类型切换 import maya.cmds as cmds cmds.selectType( polymeshFace = True ) ...
- echarts中的区域缩放组件dataZoom,主动触发选区缩放点击事件
options设置 toolbox: { // 工具栏 feature: { dataZoom : { // 选时间缩放功能 show : true, // show为true时,才能触发takeGl ...
- web-storage-cache 使用JS数据缓存
https://github.com/WQTeam/web-storage-cache 使用WebStorageCache,只要在页面上引入下面代码即可. <script src="s ...
- 1.3 正则表达式和Python语言-1.3.5使用 search()在一个字符串中查找模式(搜索与匹配 的对比)
1.3.5 使用 search()在一个字符串中查找模式(搜索与匹配的对比) 其实,想要搜索的模式出现在一个字符串中间部分的概率,远大于出现在字符串起始部分的概率.这也就是 search()派上用场的 ...
- 【C语言编程练习】新娘与新郎
1. 题目要求 新郎A,B,C与新娘 X,Y,Z.有人不知道她们谁和谁结婚了,询问了6位新人中的三位,A说他将和X结婚,X说她的未婚夫是C,C说她会和Z结婚,一听就知道是全是假话,请编程找出谁和谁结婚 ...
- 我的第一个chrome浏览器扩展 5分钟学习搞定
注意: 文件名必须是 manifest, ,注意扩展名是json, 新建一个文件夹,然后创建一个文本文件,作为这个扩展程序的配置文件,所以文件名是manifest.json, 感谢https://ww ...
- 《SpringMVC从入门到放肆》八、SpringMVC注解式开发(基本配置)
上一篇我们结束了配置式开发,配置式开发目前在企业中用的并不是很多,大部分企业都在使用注解式开发,所以今天我们就来学习注解式开发.所谓SpringMVC注解式开发是指,处理器是基于注解的类的开发方式.对 ...
- 在Codeblocks下配置GoogleTest单元测试工具
开发工具 我和我的组员的都是使用的是大一老师推荐的codeblocks,所以,就愉快的决定了工具统一为codeblocks,语言C++. 测试单元 老师推荐的是JUnit和VSTS工具,但同学们从大一 ...
- ajax源代码
//**********第一步, 获得一个xhr对象************* var xmlHttpReq = null; //声明一个空对象用来装入XMLHttpRequest if (windo ...
- DHCP工作原理简析
引言 DHCP是网络体系结构中应用层的一个重要协议,它可以帮助我们对要连接到互联网的计算机进行IP地址等信息的配置.本文从DHCP的原理出发,就DHCP的工作过程 进行详细的探讨. 主要报文 发现报文 ...