domingo, 25 de mayo de 2014

Receta No. 3.2 en C#: Crear Tipos que Operen entre Diferentes Dominios de Aplicación

Tabla de Contenido

0. Introducción
1. Problema
2. Solución
3. Discusión de la Solución
3.1 Clase MarshalByRefObject
3.2 MBV vs MBR
4. Práctica: Código Fuente C#
5. Conclusiones
6. Glosario
7. Literatura & Enlaces

0. Introducción

En esta receta vamos a aprender acerca del proceso de pase tipos entre diferentes dominios de aplicación. Aprenderemos acerca de su utilidad en ambientes que requieren el intercambio de mensajes, datos, &c., entre distintos dominios de aplicación. Esto nos llevará explorar la clase MarshalByRefObject (N:System): definición, utilidad, ejemplos. Al final veremos un ejemplo concreto en donde diferenciamos entre pasar tipos por valor y referencia en dos dominios de aplicación distintos.

1. Problema

Tenemos dos aplicaciones .NET construidas usando C#. Estas dos aplicaciones se ejecutan en dos dominios de aplicación distintos; debido a la separación por los bordes lógicos naturales que se manejan en la plataforma, requerimos de un método para poder intercomunicar-intercambiar mensajes entre las aplicaciones para pasar mensajes.

2. Solución

El Framework .NET provee un mecanismo de intercambio de datos y mensajes para aplicaciones que corren en diferentes dominios de aplicación. En esencia, podemos pasar el estado de un objeto: por referencia y por valor. En concreto:
  • marshal-by-value, y
  • marshal-by-reference.

3. Discusión de la Solución

Ya sabemos que .NET nos soluciona el caso de intercomunicación entre dos dominios de aplicación permitiéndonos pasar el estado de objetos, por referencia (marshal-by-reference) y por valor (marshal-by-value). Entonces, prestemos atención al manejo de estos dos enfoques para comprender el uso y la utilidad de estos artefactos. Empecemos por la clase System.MarhsalByRefObject.

3.1 Clase System.MarshalByRefObject

La clase MarshalByRefObject [2] permite que objetos de clase que pertenezcan a un dominio de aplicación, sobrepasen los límites (fronteras), e intercambien mensajes con otros dominios de aplicación (del mismo proceso, u otro distinto.) Para saber más acerca del proceso de creación de un dominio de aplicación, recomiendo la lectura de la receta Creación de un Dominio de Aplicación (Domain Application).

MarshalByRefObject ofrece la maquinaría necesaria para permitir el intercambio de mensajes a través de un proxy [4] (o puente). Para que un tipo de objeto pueda ser pasado por referencia a otro dominio de aplicación, es necesario que herede MarshalByRefObject. De lo contrario, de manera implícita, será tratado por valor (marshal-by-value). En este último caso, se crea una copia en el dominio de aplicación destino.

De acuerdo con [2], el acceso a los miembros de un tipo MarshalByRefObject se acceden dentro de los límites (fronteras) del dominio de aplicación local. Por otro lado, este es el proceso básico de intercomunicación entre dominios de aplicación con objetos:
  1. Acceso remoto a objeto de dominio diferente.
  2. Creación y pase de un proxy a la aplicación remota.
  3. Llamadas remotas subsecuentes al objeto en el dominio de aplicación local a través del proxy.

3.1.1 Ejemplo de uso

En este ejemplo de uso de la clase MarshalByRefObject se demostrará cómo ejecutar código en un dominio distinto al local.

Archivo UsoMarshalByRefObject.cs:

En las líneas 22-25 se declara el método VerDominio para mostrar el dominio en el que corre una instancia de Objeto. En la línea 34 se invoca al método VerDominio para mostrar el dominio de aplicación actual. De manera análoga, en la línea 42 se invoca, de nuevo, al método VerDominio para mostrar el dominio de aplicación, pero esta vez, en el nuevo dominio recién creado en la la línea 40.

> Prueba de ejecución.

Resultado:
El objeto se está ejecutando en en el AppDomain: `prog.exe`
El objeto se está ejecutando en en el AppDomain: `Nuevo Dominio`

3.2 MBV vs MBR

3.2.1 MBV

MBV (marshal-by-value), como veremos en el ejemplo de la sección 4, son tipos que para ser pasados a otro dominio de aplicación primero deben ser serializados (cfr. Persistencia de Datos de Objeto en un Archivo). Formalmente (como dicen en [1]), el sistema .NET Remoting [5, 6] se encarga de serializar (marshaling) el estado actual del objeto (realiza una copia idéntica de los datos del objeto), y lo pasa a la aplicación del dominio remoto. El resultado son dos objetos independientes, es decir, los cambios sobre el estado de un objeto no se reflejan sobre el otro.

A lo anterior, es importante mencionar el comentario de [1] respecto al paso por valor:
...This often causes confusion as you try to update the remote object are in fact updaing the local copy.

3.2.2 MBR

Ya sabemos que un tipo marshal-by-value (MBR) debe heredar de la clase MarshalByRefObject para poder ser pasado por referencia a otro dominio de aplicación. Volvamos a mencionar lo que declaramos en la sección 3.1 respecto al ciclo de pase de objetos: el sistema .NET Remoting crea un proxy (intermediario) en el dominio de aplicación destino. En la Figura 1 [1] se muestra el modo de acceso de un objeto en el modelo MBR.
Acceso a un objeto MBR.
Figura 1. Acceso a un objeto MBR.
Como se ilustra en la Figura 1, a través del proxy (intermediario), el objeto local tiene una representación en el dominio de aplicación Application Domain 2, que hace referencia a la original en el dominio de aplicación Application Domain 1.

4. Práctica: Código Fuente C#

Veamos este ejemplo en donde podemos comprobar la creación del pase un objeto por referencia y uno por valor a un dominio de aplicación distinto al local:

Archivo UsoMBVyMBR.cs:

> Prueba de ejecución.
Uso de clases MBR y MBV.
Figura 2. Uso de clases MBR y MBV.

Resultado (assembly adaptado a IDEONE: El código fuente C# anterior varía levemente respecto al de IDEONE):

Dominios de `mbvLocal` y `mbvRemoto`:
 `mbvLocal.DominioLocal`: prog.exe
 `mbvRemoto.DominioLocal`: prog.exe

Dominios de `mbrLocal` y `mbrRemoto`:
 `mbrLocal.DominioLocal`: prog.exe
 `mbrRemoto.DominioLocal`: Nuevo AppDomain

5. Conclusiones

En el transcurso de preparación de esta receta hemos aprendido varios conceptos relacionado con dominios de aplicación: intercambio de mensajes entre dominios de aplicación, uso del artefacto MarshalByRefObject (marshal-by-reference: pasa un objeto por referencia -MBR-), y marshal-by-value (MBV: pasa un objeto por valor). Además, vimos que un proxy es el intermediario de intercambio de mensajes entre el dominio de aplicación local y el remoto. Al final un ejemplo amplio de uso de MBR y MBV.

6. Glosario

  • .NET Remoting
  • Intermediario
  • Marshal-by-reference
  • Marshal-by-value
  • MBR
  • MBV
  • Proxy
  • Seralización

Literatura & Enlaces

[1]: Visual C# 2010 Recipes by Allen Jones and Adam Freeman. Copyright 2010 Allen Jones and Adam Freeman, 978-1-4302-2525-6.
[2]: MarshalByRefObject Class (System) - http://msdn.microsoft.com/en-us/library/system.marshalbyrefobject.aspx
[3]: Receta No. 3-1 en C#: Creación de un Dominio de Aplicación (Application Domain) | OrtizOL - Experiencias Construcción Software (xCSw) - http://ortizol.blogspot.com/2014/05/receta-no-3-1-en-c-creacion-de-un.html
[4]: Proxy server - Wikipedia, the free encyclopedia - http://en.wikipedia.org/wiki/Proxy_server
[5]: .NET Remoting - http://msdn.microsoft.com/en-us/library/vstudio/72x4h507(v=vs.100).aspx
[6]: .NET Remoting - Wikipedia, the free encyclopedia - http://en.wikipedia.org/wiki/.NET_Remoting
[7]: Receta No. 2-13 en C#: Persistencia de Datos de Objeto en un Archivo | OrtizOL - Experiencias Construcción Software (xCSw) - http://ortizol.blogspot.com/2014/05/receta-no-2-13-en-c-persistencia-de.html


M

No hay comentarios:

Publicar un comentario

Envíe sus comentarios, dudas, sugerencias, críticas. Gracias.