RabbitMQ学习(一).NET/C# Client之Hello World,


  • 1 "Hello World!"

    The simplest thing that doessomething

    Python | Java | Ruby | PHP| C#

前言:流行的消息队列主要有ZeroMQ(C++实现),ActiveMQ(Java实现),RabbitMQ(Erlang实现),MSMQ,Kafka,这里可以看到他们的一些评估信息:http://wiki.secondlife.com/wiki/Message_Queue_Evaluation_Notes 更多细节可以自行搜索。

Introduction


下面是RabbitMQ的一些术语:RabbitMQ是一个消息代理,实际上它从消息生产者接收消息,然后将其发送到消息消费者,在这之间可以根据特定规则对消息进行路由,缓冲,以及持久化等。

  • 生产仅仅意味着发送,一个发送消息的程序就称为生产者,比作“P”。

  • 一个队列也可以叫做邮箱,存在于RabbitMQ中,尽管消息会流过RabbitMQ以及你的应用程序,但是它仅仅会被存储在队列中。队列没有任何限制,你想存储多少消息就可以存储多少,多个生产者可以向一个消息队列发送消息,多个消费者也可以尝试从消息队列中接收(取出)消息。队列用下面的图形表示:

  • 消费和接收的意思是相同的,一个消费者就是一个等待接收消息的程序,我们用“C“表示:

记住生产者,消费者以及消息队列(Broker)不一定要存在于同一台机器上,实际上多数情况下它们都不在同一台机器上。

"Hello World"

(using the .NET/C# Client)

在这个部分将会用C#写两个程序,一个是生产者用于发送单个消息,一个是消费者用于接收消息,然后将其打印出来。我们不关注其中涉及到的.NET API的细节,集中注意力在一个简单的”Hello world“的消息上面。

(P) -> [|||] -> (C)

The .NET client library

RabbitMQ speaks AMQP, which is an open, general-purpose protocol for messaging. There are a number of clients for AMQP in many different languages. We'll use the .NET client provided by RabbitMQ.

Download the client library package, and check its signature as described. Extract it and copy "RabbitMQ.Client.dll" to your working folder.

You also need to ensure your system can find the C# compiler csc.exe, you may need to add ;C:\WINDOWS\Microsoft.NET\Framework\v3.5 (change .NET version to fit your installation) to your Path.

有了Rabbit的.NET client库之后,就可以进行下面的代码开发了:

Sending

(P) -> [|||]

我们将会编写一个消息发送者程序Send.cs以及一个消息接收程序Receive.cs,发送者将会连接到RabbitMQ,发送一个消息然后退出。

Send.cs 中,我们需要引入下面命名空间:

using System;
using RabbitMQ.Client;
using System.Text;

其中connection对象抽象了socket连接,关注协议的版本协商以及验证,这里我们连接到本地机器的RabbitMQ,所以HostName是localhost,如果我们想要连接到不同机器的broker,那么只需要将它的IP换成这个就可以。

接下来我们创建了channel对象,它几乎完成所有的事情。

要发送一个消息,我们必须要首先声明一个队列,然后才能publish(发送)消息到这个队列。

class Send
{
    public static void Main()
    {
        var factory = new ConnectionFactory() { HostName = "localhost" };
        using (var connection = factory.CreateConnection())
        {
            using (var channel = connection.CreateModel())
            {
                channel.QueueDeclare("hello", false, false, false, null);

                string message = "Hello World!";
                var body = Encoding.UTF8.GetBytes(message);

                channel.BasicPublish("", "hello", null, body);
                Console.WriteLine(" [x] Sent {0}", message);
            }
        }
    }
}

声明一个队里是幂等的(idempotent),也就是说仅仅在这个队列不存在的情况加,才会进行队列的创建操作。

消息内容是字节数组,所以在这里你需要进行编码,可以使用任何你喜欢的编码手段。

上面代码跑完之后,connection和channel对象会自动被清理(disposed)。

Here's the whole Send.cs class.

Sending doesn't work!

If this is your first time using RabbitMQ and you don't see the "Sent" message then you may be left scratching your head wondering what could be wrong. Maybe the broker was started without enough free disk space (by default it needs at least 50 MB free) and is therefore refusing to accept messages. Check the broker logfile to confirm and reduce the limit if necessary. The configuration file documentation will show you how to setdisk_free_limit.

Receiving

消息发送者发送了消息之后,消息接收者将会被RabbitMQ进行消息推送,所以和消息发送者发送一个消息不同,消息接收者需要保持对消息的监听,然后才能收到这个消息进行打印。

[|||] -> (C)

Receive.cs所需要引入的命名空间几乎和Send.cs一样:

using RabbitMQ.Client;
using RabbitMQ.Client.Events;
using System;
using System.Text;

初始化部分和Send.cs基本一样,也是打开connection和channel,然后声明消费者将要消费的消息队列。

记住接收者也需要先声明队列,因为它可能在发送者之前启动,这个时候队列可能不存在,是不能够进行告诉RabbitMQ进行监听的。

然后创建一个回调函数对象,因为消息会异步到达,所以我们告诉RabbitMQ server将消息队列hello的消息推送给我们的同时,注册了这个回调函数对象,让其可以在消息到达时进行异步调用。

class Receive
{
    public static void Main()
    {
        var factory = new ConnectionFactory() { HostName = "localhost" };
        using (var connection = factory.CreateConnection())
        {
            using (var channel = connection.CreateModel())
            {
                channel.QueueDeclare("hello", false, false, false, null);

                var consumer = new QueueingBasicConsumer(channel);
                channel.BasicConsume("hello", true, consumer);

                Console.WriteLine(" [*] Waiting for messages." +
                                         "To exit press CTRL+C");
                while (true)
                {
                    var ea = (BasicDeliverEventArgs)consumer.Queue.Dequeue();

                    var body = ea.Body;
                    var message = Encoding.UTF8.GetString(body);
                    Console.WriteLine(" [x] Received {0}", message);
                }
            }
        }
    }
}

QueueingBasicConsumer.Queue.Dequeue() blocks until another message has been delivered from the server.

Here's the whole Receive.cs class.

Putting it all together

你可以通过引用RabbitMQ 的.NET客户端DLL来编译这两个文件,我们使用的是命令行(cmd.exe and csc)来进行编译,你也可以使用Visual Studio.

$ csc /r:"RabbitMQ.Client.dll" Send.cs
$ csc /r:"RabbitMQ.Client.dll" Receive.cs

Then run the executable

$ Send.exe

then, run the receiver:

$ Receive.exe

消息接收者将会打印消息发送者通过RabbitMQ发送的消息,消息接收者也会保持运行状态,继续等待接收消息。

假如你想要查看队列情况,可以使用rabbitmqctl list_queues命令。

Hello World!


原文:http://www.rabbitmq.com/tutorials/tutorial-one-dotnet.html


怎应用NET中的消息队列服务

建立一个队列是应用MSMQ的第一步。您可以通过Windows计算机管理控制台中的消息队列选项完成这一操作,或者自己编程建立一个队列。列表A中的C#代码建立了一个新的私有MSMQ消息队列(如果不存在队列),并同时创建一条消息。代码应用MessageQueue类的Exists方法来确定是否存在一个名为TechRepublic的私有队列。如存在,它用现有队列示例这个MessageQueue对象;否则,就建立一个新队列。 新的Message对象用来向队列发送一条消息。它的Label属性指定在MSMQ控制台中显示的消息标题,其主体包含存放在队列上的项目内容。在这种情况下,我只发送文本,但您能够使用任何类型的对象。MessageQueue类的Send方法向队列发送消息。列表B中是对应的VB.NET代码。 下一步即从队列中读取消息。这是一个简单的过程,应用MessageQueue类的Receive方法即可。如果队列中存在消息,Receive方法就返回一个消息对象;否则,它等待一条消息出现(您可以设置一个时间期限)。从队列中恢复对象需要预先知道它的类型。 MessageQueue类的Formatter属性允许您轻松指定被恢复对象的类型。下面的简单例子仅使用文本,所以它应用System.String。在列表C中,C#代码从测试队列中读取消息。 提交给Receive方法的TimeSpan对象指定异常出现时系统的等待时间。接下来设置这个例子中的Formatter方法,对象被转换成字符串读取前面存储的文本。Receive方法从队列中读取消息,它的值显示在控制台中。在try块的最后部分,队列关闭。 轻松应用消息 MSMQ组合Windows和.NET的System.Messaging命名空间,使您可以方便地在.NET应用程序中利用消息。消息提供一种在企业应用程序中异步发送并接收消息(数据)的强大工具。
 

net中怎使用消息队列?

先要在工程中引用 System.Messaging
然后才在文件里面写 using System.Messaging
 

相关内容