C# 如何使用 RabbitMQ 实现消息收发
本文是基于http://www.cnblogs.com/cheng-lei/articles/7274513.html的项目结构进行搭建的,了解之前请先阅读http://www.cnblogs.com/cheng-lei/category/1047427.html中的前四篇文章。
工具 — Nuget包管理器 —程序包管理器控制台
PM> Install-Package RabbitMQ.Client -Version 5.1.0
PM> Install-Package EasyNetQ -Version 3.2.0
一、项目搭建
1. Weiz.MQ 项目,消息队列的通用处理类库,用于正在的订阅和发布消息。
1、在BusBuilder.cs中添加了对CreateAdvancedBus函数的实现。
public static IAdvancedBus CreateAdvancedBus()
{
// 消息服务器连接字符串
string connString = "host=dev.corp.wingoht.com:5672;virtualHost=cd;username=ishowfun;password=123456";
if (connString == null || connString == string.Empty)
{
throw new Exception("messageserver connection string is missing or empty");
} return RabbitHutch.CreateBus(connString).Advanced;
}
2、在MQHelper.cs中添加了对Send、Receive函数的实现。
public static void Send(MyMessage msg)
{
// 创建消息bus
IBus bus = BusBuilder.CreateMessageBus(); try
{
bus.Send(msg.MessageRouter, msg);
}
catch (EasyNetQException ex)
{
//处理连接消息服务器异常
Console.WriteLine("Send Error!!!");
} bus.Dispose();//与数据库connection类似,使用后记得销毁bus对象
} public static void Receive(MyMessage msg, IProcessMessage ipro)
{
// 创建消息bus
IBus bus = BusBuilder.CreateMessageBus(); try
{
bus.Receive<MyMessage>(msg.MessageRouter, message => ipro.ProcessMsg(message));
}
catch (EasyNetQException ex)
{
//处理连接消息服务器异常
Console.WriteLine("Receive Error!!!");
}
}
3、在MQHelper.cs中添加了对采用Fanout、Direct、Topic交换机类型进行消息收发功能的实现。
public static void ProducerFanoutMessage(MyMessage msg, string exchangeName = "chending.fanout")
{
var advancedBus = BusBuilder.CreateAdvancedBus(); if (advancedBus.IsConnected)
{
var exchange = advancedBus.ExchangeDeclare(exchangeName, ExchangeType.Fanout); advancedBus.Publish(exchange, "", false, new Message<MyMessage>(msg));
}
else
{
Console.WriteLine("Can't connect");
} } public static void ConsumeFanoutMessage(string exchageName = "chending.fanout", string queueName = "chending.fanout.queue")
{
var advancedBus = BusBuilder.CreateAdvancedBus();
var exchange = advancedBus.ExchangeDeclare(exchageName, ExchangeType.Fanout); var queue = advancedBus.QueueDeclare(queueName);
advancedBus.Bind(exchange, queue, queueName);
advancedBus.Consume(queue, registration =>
{
registration.Add<MyMessage>((message, info) => { Console.WriteLine("Fanout Content: {0}", message.Body.MessageBody); });
});
} public static void ProducerDirectMessage(MyMessage msg, string queueName = "chending.direct.queue")
{
var advancedBus = BusBuilder.CreateAdvancedBus(); if (advancedBus.IsConnected)
{
var queue = advancedBus.QueueDeclare(queueName); advancedBus.Publish(Exchange.GetDefault(), queue.Name, false, new Message<MyMessage>(msg));
}
else
{
Console.WriteLine("Can't connect");
} } public static void ConsumeDirectMessage(string exchageName = "chending.direct", string queueName = "chending.direct.queue")
{
var advancedBus = BusBuilder.CreateAdvancedBus();
var exchange = advancedBus.ExchangeDeclare(exchageName, ExchangeType.Direct); var queue = advancedBus.QueueDeclare(queueName);
advancedBus.Bind(exchange, queue, queueName);
advancedBus.Consume(queue, registration =>
{
registration.Add<MyMessage>((message, info) => { Console.WriteLine("Direct Content: {0}", message.Body.MessageBody); });
});
} public static void ProducerTopicMessage(MyMessage msg)
{
//// 创建消息bus
IBus bus = BusBuilder.CreateMessageBus(); try
{
bus.Publish(msg, x => x.WithTopic(msg.MessageRouter));
}
catch (EasyNetQException ex)
{
//处理连接消息服务器异常
} bus.Dispose();//与数据库connection类似,使用后记得销毁bus对象
} public static void ConsumeTopicMessage(MyMessage msg)
{
//// 创建消息bus
IBus bus = BusBuilder.CreateMessageBus(); try
{
bus.Subscribe<MyMessage>(msg.MessageRouter, message => Console.WriteLine("Topic Content: {0}", message.MessageBody), x => x.WithTopic(msg.MessageRouter));
}
catch (EasyNetQException ex)
{
//处理连接消息服务器异常
}
}
4、在ProduceThread.cs中添加了消息发布线程对前面实现的功能进行测试(也可以不作为线程直接调用)。
public class ProduceThread
{
public static void ProduceMessage() {
MyMessage msg1 = new MyMessage();
msg1.MessageID = "0-1";
msg1.MessageBody = DateTime.Now.ToString();
msg1.MessageRouter = "chending.fanout";
msg1.MessageTitle = "0-1";
MyMessage msg2 = new MyMessage();
msg2.MessageID = "0-2";
msg2.MessageBody = DateTime.Now.ToString();
msg2.MessageRouter = "chending.direct";
msg2.MessageTitle = "0-2";
MyMessage msg3 = new MyMessage();
msg3.MessageID = "0-3";
msg3.MessageBody = DateTime.Now.ToString();
msg3.MessageRouter = "chending.topic.a.b";
msg3.MessageTitle = "0-3"; //MQHelper.Send(msg1);
MQHelper.ProducerFanoutMessage(msg1);
MQHelper.ProducerDirectMessage(msg2);
MQHelper.ProducerTopicMessage(msg3); for (int i = ; i < ; i++) {
MyMessage msg = new MyMessage();
msg.MessageID = (i+).ToString();
msg.MessageBody = DateTime.Now.ToString();
if (i % == )
msg.MessageRouter = "cd.test.demo.a.b";
else
msg.MessageRouter = "cd.test.demo.a";
msg.MessageTitle = (i+).ToString(); MQHelper.Publish(msg);
//Console.WriteLine("Message{0} is published!!!", i + 1);
Thread.Sleep();
}
}
2. Weiz.Producer(生成者)已弃用(改用ProduceThread.cs)
3. Weiz.Consumer 就是Consumer(消费者)
1、修改OrderProcessMessage.cs,实现不同的消息处理方式。
public class OrderProcessMessage : MQ.IProcessMessage
{
public void ProcessMsg(MQ.MyMessage msg)
{
Console.WriteLine("ID: {0}, Title: {1}, Router: {2}, Content: {3}", msg.MessageID, msg.MessageTitle, msg.MessageRouter, msg.MessageBody);
}
}
public class OrderProcessMessage1:MQ.IProcessMessage
{
public void ProcessMsg(MQ.MyMessage msg)
{
Console.WriteLine("Process1 ID: {0}, Title: {1}, Router: {2}, Content: {3}", msg.MessageID, msg.MessageTitle, msg.MessageRouter, msg.MessageBody);
}
} public class OrderProcessMessage2 : MQ.IProcessMessage
{
public void ProcessMsg(MQ.MyMessage msg)
{
Console.WriteLine("Process2 ID: {0}, Title: {1}, Router: {2}, Content: {3}", msg.MessageID, msg.MessageTitle, msg.MessageRouter, msg.MessageBody);
}
}
2、对Program.cs中的Main调用进行了修改。
class Program
{
static void Main(string[] args)
{
//OrderProcessMessage order = new OrderProcessMessage();
OrderProcessMessage1 order1 = new OrderProcessMessage1();
OrderProcessMessage2 order2 = new OrderProcessMessage2(); //MyMessage msg = new MyMessage();
MyMessage msg1 = new MyMessage();
MyMessage msg2 = new MyMessage();
MyMessage msg3 = new MyMessage(); //msg.MessageRouter = "cd.test.demo";
msg1.MessageRouter = "cd.test.demo.*";
msg2.MessageRouter = "cd.test.demo.#";
msg3.MessageRouter = "chending.topic.#"; //MQHelper.Receive(msg, order);
MQHelper.ConsumeFanoutMessage();
MQHelper.ConsumeDirectMessage();
MQHelper.ConsumeTopicMessage(msg3);
MQHelper.Subscribe(msg1, order1);
//MQHelper.Subscribe(msg1, order2);
MQHelper.Subscribe(msg2, order2); Console.WriteLine("Listening for messages."); ProduceThread.ProduceMessage(); //ThreadStart threadStart = ProduceThread.ProduceMessage;
//Thread thread = new Thread(threadStart);
//thread.Start();
}
}
二、项目运行
启动 Weiz.Consumer (消费者),启动消费者,会自动在RabbitMQ 服务器上创建相关的exchange 和 queue ,同时调用的ProduceThread.ProduceMessage函数会发送消息,接收到的信息会在Console命令行中进行显示。
项目源码:百度云链接:https://pan.baidu.com/s/1sCJqY2fKphXV0ntMIytcVw 密码:hfz5
C# 如何使用 RabbitMQ 实现消息收发的更多相关文章
- 通过集群的方式解决基于MQTT协议的RabbitMQ消息收发
在完成了基于AMQP协议的RabbitMQ消息收发后,我们要继续实现基于MQTT协议的RabbitMQ消息收发. 由于C#的RabbitMQ.Client包中只实现了基于AMQP协议的消息收发功能的封 ...
- 第五节 RabbitMQ在C#端的应用-消息收发
原文:第五节 RabbitMQ在C#端的应用-消息收发 版权声明:未经本人同意,不得转载该文章,谢谢 https://blog.csdn.net/phocus1/article/details/873 ...
- RabbitMQ入门-消息订阅模式
消息派发 上篇<RabbitMQ入门-消息派发那些事儿>发布之后,收了不少反馈,其中问的最多的还是有关消息确认以及超时等场景的处理. 楼主,有遇到消费者后台进程不在,但consumer连接 ...
- rabbitmq(中间消息代理)在python中的使用
在之前的有关线程,进程的博客中,我们介绍了它们各自在同一个程序中的通信方法.但是不同程序,甚至不同编程语言所写的应用软件之间的通信,以前所介绍的线程.进程队列便不再适用了:此种情况便只能使用socke ...
- 整合Spring Cloud Stream Binder与RabbitMQ进行消息发送与接收
我最新最全的文章都在南瓜慢说 www.pkslow.com,欢迎大家来喝茶! 1 前言 Spring Cloud Stream专门用于事件驱动的微服务系统,使用消息中间件来收发信息.使用Spring ...
- RabbitMQ:消息丢失 | 消息重复 | 消息积压的原因+解决方案+网上学不到的使用心得
前言 首先说一点,企业中最常用的实际上既不是RocketMQ,也不是Kafka,而是RabbitMQ. RocketMQ很强大,但主要是阿里推广自己的云产品而开源出来的一款消息队列,其实中小企业用Ro ...
- twsited(5)--不同模块用rabbitmq传递消息
上一章,我们讲到,用redis共享数据,以及用redis中的队列来实现一个简单的消息传递.其实在真实的过程中,不应该用redis来传递,最好用专业的消息队列,我们python中,用到最广泛的就是rab ...
- 如何在项目中引入MetaQ消息收发机制
当需要异步发送和接收大量消息时,需要在Crystal项目中引入MetaQ消息收发机制. 关于MetaQ使用的官方例子可参考:https://github.com/killme2008/Metamorp ...
- RabbitMQ分布式消息队列服务器(一、Windows下安装和部署)
RabbitMQ消息队列服务器在Windows下的安装和部署-> 一.Erlang语言环境的搭建 RabbitMQ开源消息队列服务是使用Erlang语言开发的,因此我们要使用他就必须先进行Erl ...
随机推荐
- 学习一份百度的JavaScript编码规范
JavaScript编码规范 1 前言 2 代码风格 2.1 文件 2.2 结构 2.2.1 缩进 2.2.2 空格 2.2.3 换行 2.2.4 语句 2.3 命名 2.4 注释 2.4.1 单行注 ...
- 如何转换Xcode里打印的unicode编码日志
转换Xcode里打印的unicode编码日志 1)打开Terminal 2)输入python 3)print(u'\u6027\u611f\u597d\u83b1\u575e\u5973\u661f\ ...
- Notes 20180507 : Java程序设计之环境搭建与HelloWord
3 HelloWorld 不管从事什么工作那么一个工作环境总是必不可少的,那怕你只是要写篇文章,一张平坦的书桌和流利的书写笔总是能帮助我们完成工作的,Java开发更是如此.在开始今天的HelloWor ...
- C# 反射 Reflection Assembly
本章节带来的是反射,反射反射程序员的快乐. 一.什么叫反射 反射:是.net Framework提供给的一个方面metadata的帮助类,可以获取信息并且使用 反射的有点:动态 反射的缺点:1:稍微麻 ...
- ueditor getshell漏洞重现及分析
0x00 概述 8月21日,网上爆出ueditor .net版本getshell漏洞,由于只校验ContentType而没校验文件后缀导致getshell. 0x01 漏洞重现 Payload: &l ...
- ElasticSearch优化系列三:机器设置(内存)
heap参数设置优化 命令行修改 ./bin/elasticsearch -Xmx10g -Xms10g xmx-JVM最大允许分配的堆内存,按需分配 xms-JVM初始分配的堆内存 此值设置与-Xm ...
- .net下redis和rabbitmq简单使用demo
是参考 一下两篇博文整理了下. Redis: https://www.cnblogs.com/5ishare/p/6492380.html RabbitMq: https://www.cnbl ...
- BurpSuite系列(十)----Extender模块(扩展器)
一.简介 Burp在软件中提供了支持第三方拓展插件的功能,方便使用者编写自己的自定义插件或从插件商店中安装拓展插件.Burp扩展程序可以以多种方式支持自定义Burp的行为,例如:修改HTTP请求和响应 ...
- R语言(自定义函数、循环语句、管道函数)
学习R语言半年多了,以前比较注重统计方法上的学习,但是最近感觉一些基础知识也很重要.去年的参考资料是<R语言实战>,今年主要是看视频.推荐网易云课堂里的教程,很多资料都是很良心的~ 目前学 ...
- pentestbox更新msf
pentestbox成功升级msf 1. 输入 msfupdate 进行软件更新 2. 在[*] Updating gems...,软件报错,提示找不到文件路径,输入以下两条命令,尝试单独安装 g ...