1. 程式人生 > >消息隊列MSMQ的使用

消息隊列MSMQ的使用

gif msm 發送消息 body 關閉window adl console 使用 復制

1.MSMQ安裝

控制面板-程序和功能-打開或關閉Windows功能-Microsoft Message Queue(MSMQ)服務器,選中所有,點擊確定。

2.消息隊列的應用場景(轉載自http://www.cnblogs.com/stopfalling/p/5375492.html)

①異步處理

②應用解耦

③流量削鋒

④日誌處理

⑤消息通訊

3.MSMQ消息分為事務性和非事務性

非事務性的消息保存在內存中,機器重啟後丟失消息隊列中的消息。

事務性的消息經過了持久化,保存在硬盤中,機器重啟後隊列中的消息不會丟失。

4.測試代碼

消息發送方

技術分享圖片
namespace MessageQueueSender
{
    class Program
    {
        static void Main(string[] args)
        {
            MessageQueue MSMQ = CreateMessageQueue(@".\private$\tpmsmq");
            MSMQ.Formatter = new XmlMessageFormatter(new Type[] { typeof(string) });

            Console.WriteLine("是否繼續發送消息:Y/N?");
            string cmd = Console.ReadLine();

            while (cmd.Equals("Y"))
            {
                Sender(MSMQ);

                Console.WriteLine("是否繼續發送消息:Y/N?");
                cmd = Console.ReadLine();
            }

            Console.WriteLine("按任意鍵以停止...");
            Console.ReadKey();
        }
        private static void Sender(MessageQueue MSMQ)
        {
            try
            {
                string random = GenerateRandom();
                string obj = string.Format("{0} 發送方:{1}",
                    DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"), random);

                MSMQ.Send(obj, MessageQueueTransactionType.Single);

                Console.WriteLine(obj);

            }
            catch (Exception ex)
            {
                Console.WriteLine(string.Format("{0} 發送方:{1}",
                DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"), ex.Message));
            }
        }

        public static MessageQueue CreateMessageQueue(string path)
        {
            MessageQueue mq = null;

            if (MessageQueue.Exists(path))
            {
                mq = new MessageQueue(path);
            }
            else
            {
                mq = MessageQueue.Create(path, true);
            }

            return mq;
        }

        public static string GenerateRandom()
        {
            int seed = GetRandomSeed();
            return new Random(seed)
                .Next(Int32.MaxValue).ToString();
        }

        /// <summary>
        /// 創建加密隨機數生成器 生成強隨機種子
        /// </summary>
        /// <returns></returns>
        private static int GetRandomSeed()
        {
            byte[] bytes = new byte[4];
            System.Security.Cryptography.RNGCryptoServiceProvider rng
                = new System.Security.Cryptography.RNGCryptoServiceProvider();
            rng.GetBytes(bytes);
            return BitConverter.ToInt32(bytes, 0);
        }
    }


}
技術分享圖片

消息接收方

技術分享圖片
namespace MessageQueueReceiver
{
    class Program
    {
        static void Main(string[] args)
        {
            MessageQueue MSMQ = CreateMessageQueue(@".\private$\tpmsmq");
            MSMQ.Formatter = new XmlMessageFormatter(new Type[] { typeof(string) });

            Receiver(MSMQ);
        }

        private static void Receiver(MessageQueue MSMQ)
        {
            while (true)
            {
                try
                {
                    Message m = MSMQ.Receive(MessageQueueTransactionType.Single);
                    Console.WriteLine(string.Format("{0} 接收方:[{1}]",
                        DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"), m.Body.ToString()));
                }
                catch (Exception ex)
                {
                    Console.WriteLine(string.Format("{0} 接收方:{1}",
                    DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"), ex.Message));
                }
            }
        }

        public static MessageQueue CreateMessageQueue(string path)
        {
            MessageQueue mq = null;

            if (MessageQueue.Exists(path))
            {
                mq = new MessageQueue(path);
            }
            else
            {
                mq = MessageQueue.Create(path, true);
            }

            return mq;
        }
    }
}
技術分享圖片

MessageQueue.Receive()方法是同步執行的,如果隊列中沒有消息,則會造成阻塞,程序會停止在這塊,等待消息的產生。

消息隊列MSMQ的使用