Cómo trabajar con MSMQ en C #

MSMQ (Microsoft Message Queue Server) es una cola de mensajes que está disponible de forma predeterminada como parte de Windows. Una forma confiable de enviar y recibir mensajes a través de sistemas informáticos, MSMQ proporciona una cola que es escalable, segura para subprocesos, simple y conveniente de usar mientras que al mismo tiempo le brinda la oportunidad de conservar los mensajes dentro de la base de datos de Windows. MSDN afirma: "La tecnología Message Queue Server (MSMQ) permite que las aplicaciones que se ejecutan en diferentes momentos se comuniquen a través de redes heterogéneas y sistemas que pueden estar temporalmente fuera de línea. Las aplicaciones envían mensajes a las colas y leen los mensajes de las colas".

Normalmente, tiene dos aplicaciones distintas cuando trabaja con MSMQ: el remitente y el receptor. Cuando los mensajes son enviados por el remitente, es decir, la aplicación emisora, la aplicación receptora no necesita estar en estado de ejecución; los mensajes se almacenan en una cola mantenida por el sistema operativo host y se retiran de la cola cuando son necesarios para la aplicación receptora.

Crear una cola

Puede activar MSMQ en su sistema a través de la opción "Activar o desactivar las funciones de Windows" del panel de control. Una vez que MSMQ se ha instalado en su sistema, crear una cola es simple. Simplemente vaya a "Mi PC", haga clic derecho y seleccione Administrar. En la ventana "Administración de equipos" puede crear una nueva cola desde el nodo "Message Queue Server". También puede crear una cola mediante programación.

Programación de MSMQ en C #

Para trabajar con MSMQ, deberá incluir el espacio de nombres System.Messaging. Para crear una cola mediante programación, debe aprovechar el método Create de la clase MessageQueue. El siguiente fragmento de código ilustra esto.

MessageQueue.Create(@".\Private$\");

Para crear una cola y enviarle un mensaje, puede utilizar el siguiente fragmento de código.

MessageQueue.Create(@".\Private$\");              

messageQueue = new MessageQueue(@".\Private$\");

messageQueue.Label = "This is a test queue.";

messageQueue.Send("This is a test message.", "");

Ahora, suponga que le gustaría comprobar si la cola existe y, si existe, enviarle un mensaje. Si la cola no existe, es posible que desee crear una nueva y luego enviarle un mensaje. Esto es exactamente lo que hace la siguiente lista de códigos.

static void Main(string[] args)

        {

            MessageQueue messageQueue = null;

            string description = "This is a test queue.";

            string message = "This is a test message.";

            string path = @".\Private$\";

            try

            {

                if (MessageQueue.Exists(path))

                {

                    messageQueue = new MessageQueue(path);

                    messageQueue.Label = description;

                }

                else

                {

                    MessageQueue.Create(path);

                    messageQueue = new MessageQueue(path);

                    messageQueue.Label = description;

                }

                messageQueue.Send(message);

            }

            catch

            {

                throw;

            }

finally

{

           messageQueue.Dispose();

}

      }

La siguiente lista de códigos ilustra cómo puede procesar los mensajes almacenados en una cola de mensajes usando C #.

private static List ReadQueue(string path)

        {

            List lstMessages = new List();

            using (MessageQueue messageQueue = new MessageQueue(path))

            {

                System.Messaging.Message[] messages = messageQueue.GetAllMessages();

                foreach (System.Messaging.Message message in messages)

                {

                    message.Formatter = new XmlMessageFormatter(

                    new String[] { "System.String, mscorlib" });

                    string msg = message.Body.ToString();

                    lstMessages.Add(msg);

                }

            }

            return lstMessages;

        }

A continuación, puede invocar el método ReadQueue para recuperar los mensajes almacenados en la cola de mensajes como se muestra en el fragmento de código a continuación.

string path = @".\Private$\";

List lstMessages = ReadQueue(path);

También puede almacenar objetos en la cola de mensajes. Como ejemplo, suponga que necesita almacenar un mensaje de registro en la cola. El mensaje de registro se almacena en una instancia de la clase LogMessage que contiene las propiedades necesarias que pertenecen a los detalles del mensaje de registro. Así es como se vería la clase LogMessage: lo he simplificado con solo dos propiedades.

public class LogMessage

    {

        public string MessageText { get; set; }

        public DateTime MessageTime { get; set; }

    }

Debe modificar la clase LogMessage para incorporar otras propiedades necesarias, es decir, la gravedad del mensaje, etc. El siguiente método ilustra cómo puede almacenar una instancia de la clase LogMessage en la cola de mensajes.

private static void SendMessage(string queueName, LogMessage msg)

        {

            MessageQueue messageQueue = null;

            if (!MessageQueue.Exists(queueName))

                messageQueue = MessageQueue.Create(queueName);

            else

                messageQueue = new MessageQueue(queueName);          

            try

            {

                messageQueue.Formatter = new XmlMessageFormatter(new Type[] { typeof(LogMessage) });

                messageQueue.Send(msg);

            }

            catch

            {

                //Write code here to do the necessary error handling.

            }

            finally

            {

                messageQueue.Close();

            }          

        }

El siguiente fragmento de código ilustra cómo puede crear una instancia de la clase LogMessage, completarla con datos y luego invocar el método SendMessage para almacenar la instancia creada en la cola de mensajes.

LogMessage msg = new LogMessage()

            {

                MessageText = "This is a test message.",

                MessageTime = DateTime.Now

            };

SendMessage(@".\Private$\Log", msg);

La siguiente lista de códigos ilustra cómo puede leer la instancia de LogMessage almacenada en la cola de mensajes.

private static LogMessage ReceiveMessage(string queueName)

        {

            if (!MessageQueue.Exists(queueName))

                return null;

            MessageQueue messageQueue = new MessageQueue(queueName);

            LogMessage logMessage = null;

            try

            {

                messageQueue.Formatter = new XmlMessageFormatter(new Type[] { typeof(LogMessage) });

                logMessage = (LogMessage)messageQueue.Receive().Body;

            }

            catch { }

            finally

            {

                messageQueue.Close();

            }

            return logMessage;

        }