http://www.cnblogs.com/Ansel/archive/2005/11/28/286073.html
簡介
MSMQ(微軟訊息佇列)是Windows作業系統中訊息應用程式的基礎,是用於建立分布式、鬆散串連的訊息通訊應用程式的開發工具。訊息佇列和電子郵件有著很多相似處,他們都包含多個屬性,用於儲存訊息,訊息類型中都指出寄件者和接收者的地址;然而他們的用處卻有著很大的區別:訊息佇列的寄件者和接收者是應用程式,而電子郵件的寄件者和接收者通常是人。
如同電子郵件一樣,訊息佇列的發送和接收也不需要寄件者和接收者同時在場,可以儲存在訊息佇列或是郵件伺服器中。因此,我們可以用來描述MSMQ應用程式的體繫結構:
從可以看出,開發MSMQ應用程式並不是十分困難的事情。不過要使用MSMQ開發你的訊息處理常式,必須在開發系統和使用程式的主機上安裝訊息佇列。訊息佇列的安裝屬於Windows組件的安裝,和一般的組件安裝方法類似。安裝好訊息佇列後,就可以開發你自己的訊息處理常式了。不過有一點需要注意,如果你的電腦處於工作群組中,而不是某個域中,可能你的公用佇列不能使用,不過這並不影響你的程式開發。
訊息處理常式不外乎訊息的發送和接收,然而要收發訊息,還必須引用一個隊列,通常我們引用公用佇列和專用隊列,這兩個隊列都存放使用者產生的訊息。引用隊列後,就可以發送、接收和閱讀訊息了。訊息接收服務位於System.Messaging中,如果你找不到這一命名空間,你必須手動添加。點擊[項目]中的[添加引用],按下瀏覽按鈕,找到System.Messaging.dll檔案,添加進來即可。
引用隊列
引用隊列有三種方法,通過路徑、格式名和標籤引用隊列,這裡我只介紹最簡單和最常用的方法:通過路徑應用隊列。隊列路徑的形式為 machinenamequeuename。指向隊列的路徑總是唯一的。下表列出用於每種類型的隊列的路徑資訊:
隊列類型 |
路徑中使用的文法 |
公用隊列 |
MachineNameQueueName |
專用隊列 |
MachineNamePrivate$QueueName |
日誌隊列 |
MachineNameQueueNameJournal$ |
如果是發送到本機上,還可以使用”.”代表本機名稱。具體的引用方法通過Path屬性來進行,也可以在初始化訊息佇列時進行。
如果在初始化時引用訊息佇列,那麼訊息佇列必須存在於系統中,否則會產生中斷。往系統中添加隊列十分的簡單,開啟[控制台]中的[電腦管理],展開[服務和應用程式],找到並展開[訊息佇列](如果找不到,說明你還沒有安裝訊息佇列),右擊希望添加的訊息佇列的類別,選擇建立隊列即可。當然,在程式中也可以實現訊息佇列的建立,下文會有相應的說明。在初始化時引用訊息佇列的代碼很簡單,如下所示:
MessageQueue Mq=new MessageQueue(“.\private$\jiang”);
通過Path屬性引用訊息佇列的代碼也十分簡單:
MessageQueue Mq=new MessageQueue();
Mq.Path=”.\private$\jiang”;
使用 Create 方法可以在電腦上建立隊列:
System.Messaging.MessageQueue.Create(@".private$jiang");
發送訊息
隊列引用過後,就可以發送訊息了。訊息的發送可以分為簡單訊息和複雜訊息,簡單訊息類型就是常用的資料類型,例如整型、字串等資料;複雜訊息的資料類型通常對應於系統中的複雜資料類型,例如結構,對象等等。
簡單訊息的發送樣本如下:
Mq.Send(1000); //發送整型資料
Mq.Send(“This is a test message!”); //發送字串
複雜訊息的發送和簡單訊息的發送大同小異,只是發送時,通常不是直接給出發送的訊息內容,而是代表發送訊息內容的變數。下面的代碼分別通過訊息變數和複雜資料類型變數發送一條複雜訊息。
//下面的代碼中發送的訊息由訊息變數表示
Message Msg;
Msg=new Message(“A Complex Message!”);
Msg.Label=”This is the label”;
Msg.Priority=MessagePriority.High;
Mq.Send(Msg);
//下面的代碼中發送的訊息由複雜資料類型變數表示,Customer為自訂的一個類
Customer customer = new Customer();
customer.LastName = "Copernicus";
customer.FirstName = "Nicolaus";
Mq.Send(customer);
接收訊息
接收訊息相比發送訊息要複雜一點。接收訊息由兩種方式:通過Receive方法接收訊息同時永久性地從隊列中刪除訊息;通過Peek方法從隊列中取出訊息而不從隊列中移除該訊息。如果知道訊息的標識符(ID),還可以通過ReceiveById方法和PeekById方法完成相應的操作。
接收訊息的代碼很簡單:
Mq.Receive(); //或Mq.ReceiveById(ID);
Mq.Peek(); // 或Mq.PeekById(ID);
閱讀訊息
接收到的訊息只有能夠讀出來才是有用的訊息,因此接收到訊息以後還必須能讀出訊息,而讀出訊息算是最複雜的一部操作了。在應用程式能夠閱讀的訊息和訊息佇列中的訊息格式不同,因而應用程式發送出去的訊息經過序列化以後才發送給了訊息佇列,這一過程由系統自動完成了,程式開發人員不必為此編寫代碼,然而在接收到訊息後就面臨著訊息序列化的問題。
訊息的序列化可以通過Visual Studio 和 .NET Framework 附帶的三個預定義的格式化程式來完成:XMLMessageFormatter 對象( MessageQueue 組件的預設格式化程式設定)、BinaryMessageFormatter 對象、ActiveXMessageFormatter 對象。由於後兩者格式化後的訊息通常不能為人閱讀,所以我們經常用到的是XMLMessageFormatter對象。
使用XMLMessageFormatter對象格式化訊息的代碼如下所示:
string[] types = { "System.String" };
((XmlMessageFormatter)mq.Formatter).TargetTypeNames = types;
Message m=mq.Receive(new TimeSpan(0,0,3));
將接收到的訊息傳送給訊息變數以後,通過訊息變數m的Body屬性就可以讀出訊息了:
MessageBox.Show((string)m.Body);