Indice general de los manuales

  1. Introducción, instalación en Ubuntu y creación de una calculadora.
  2. Modos de compartición de objetos. Creando nuestra primera calculadora distribuida.
    1. Modos de compartición de objetos: Singlecall.
    2. Modos de compartición de objetos: Singleton.
    3. Modos de compartición de objetos: CAO.
  3. Canales: TCP y HTTP. Configuración en archivo XML.  «  [Leyendo]
  4. Uso de interfaces para separar el código entre cliente y servidor.

Introducción

Ya que tenemos una buena base, e incluso ya podríamos hacer nuestros programillas, ahora estudiaremos algunas cosas que nos pueden ser interesantes y de gran ayuda. Aprenderemos dos cosas:

  • Compartiremos los objetos mediante el canal TCP, en lugar de HTTP como hemos ido haciendo anteriormente.
  • Guardaremos la configuración de como comparte el servidor los objetos en un archivo, ya que, de esta forma, no tendremos que compilar el servidor o el cliente) cada vez que decidamos si queremos un SingleCall, un Singleton o un CAO; y también la dirección, el puerto, etc.

1. Usando el canal TCP

Usar el canal TCP es tan fácil como usar HTTP. De hecho, si echamos un vistazo a códigos anteriores, podríamos intuir cómo usarlo.

Cogeremos el código del servidor de alguno de los ejemplos anteriores para ver el cambio:

  1. // Archivo: Servidor.cs
  2. // Descripcion: programa servidor que comparte
  3. // la clase Calculadora remotamente.
  4.  
  5. // Biblioteca estandar y remoting
  6. using System;
  7. using System.Runtime.Remoting;
  8.  
  9. // Clases de Remoting
  10. using System.Runtime.Remoting.Channels;
  11. using System.Runtime.Remoting.Channels.Http;
  12.  
  13. namespace Servidor
  14. {
  15.   public class Servidor
  16.   {
  17.     // arg[0] representa el puerto del servidor
  18.     public static void Main(string[] args)
  19.     {
  20.       // Creamos un nuevo objeto para el canal HTTP
  21.       HttpChannel chnl = new HttpChannel(int.Parse(args[0]));
  22.  
  23.       // Le decimos a la máquina que nos reserve ese canal
  24.       ChannelServices.RegisterChannel(chnl);
  25.  
  26.       // Opciones para la comparticion de la clase
  27.       RemotingConfiguration.RegisterWellKnownServiceType(
  28.         typeof(Calculo.Calculadora),
  29.         “Calculadora.remota”,
  30.         WellKnownObjectMode.SingleCall);
  31.  
  32.       // Mensajes de espera en la pantalla
  33.       Console.WriteLine(“Atendiendo las peticiones…”);
  34.       Console.WriteLine(“Pulse Enter para salir…”);
  35.       Console.ReadLine();
  36.     }
  37.   }
  38. }

Como vemos en el ejemplo, estamos usando siempre HTTP. El código para usar el canal TCP consistirá en cambiar las apariciones de “Http” por “Tcp”, así de simple. Podemos verlo en el siguiente ejemplo del código anterior modificado:

  1. // Archivo: Servidor.cs
  2. // Descripcion: programa servidor que comparte
  3. // la clase Calculadora remotamente.
  4.  
  5. // Biblioteca estandar y remoting
  6. using System;
  7. using System.Runtime.Remoting;
  8.  
  9. // Clases de Remoting
  10. using System.Runtime.Remoting.Channels;
  11. using System.Runtime.Remoting.Channels.Tcp;
  12.  
  13. namespace Servidor
  14. {
  15.   public class Servidor
  16.   {
  17.     // arg[0] representa el puerto del servidor
  18.     public static void Main(string[] args)
  19.     {
  20.       // Creamos un nuevo objeto para el canal TCP (antes era HTTP)
  21.       TcpChannel chnl = new TcpChannel(int.Parse(args[0]));
  22.  
  23.       // Le decimos a la máquina que nos reserve ese canal
  24.       ChannelServices.RegisterChannel(chnl);
  25.  
  26.       // Opciones para la comparticion de la clase
  27.       RemotingConfiguration.RegisterWellKnownServiceType(
  28.         typeof(Calculo.Calculadora),
  29.         “Calculadora.remota”,
  30.         WellKnownObjectMode.SingleCall);
  31.  
  32.       // Mensajes de espera en la pantalla
  33.       Console.WriteLine(“Atendiendo las peticiones…”);
  34.       Console.WriteLine(“Pulse Enter para salir…”);
  35.       Console.ReadLine();
  36.     }
  37.   }
  38. }

1.1. ¿En qué se diferencian los dos canales?

Canal HTTP: Los mensajes que recibimos y envía el objeto remoto usarán el protocolo SOAP, es decir, estos datos se convertirán en formato SOAP (Simple Object Access Protocol) para comunicarse entre sí. El protocolo SOAP es una representación de la comunicación entre dos objetos en XML. Así pues, cuando los programas se comunicaban entre sí, lo hacían enviándose mensajes en XML que podían interpretar.

Canal TCP: es más simple, los mensajes que se usan para la comunicación se envían en binario.

1.2. ¿Cuál usar?

Mirando esta tabla, podremos escoger nuestro canal según nuestra necesidad:

Causa HTTP TCP
Rapidez Es más lento, ya que tiene que enviar mucha información en XML. Es más rápido, ya que usa binario y manda la información justamente necesaria.
Seguridad Un cortafuegos podría dejar pasar información en XML. Un cortafuegos podría denegar la entrada a información en binario.
Herramientas Se puede usar WSDL para describir los servicios web que nos ofrece el servidor (se verá más adelante).  

2. Archivos de configuración

En los ejemplos anteriores, hemos visto como la configuración del servidor y del cliente la escribíamos dentro del programa (el modo, la dirección, el puerto). Ahora veremos una forma de tener nuestra configuración en un fichero separado.

Los archivos de configuración están escritos en XML. Ahora daremos los ejemplos de configuración del servidor y del cliente que podrían sernos útiles en los ejemplos anteriores.

2.1. Archivo para el servidor

El archivo que deberá recoger el servidor debe tener una estructura similar a esta:

Archivo: Servidor.exe.config

  1. <configuration>
  2.   <system.runtime.remoting>
  3.     <application>
  4.  
  5.       <!– Clase que vamos a compartir –>
  6.       <service>
  7.         <wellknown
  8.           mode=“Singleton”
  9.           type=“Calculo.Calculadora, Calculo”
  10.           objectUri=“Calculadora.remota” />
  11.       </service>
  12.  
  13.       <!– Canales que vamos a utilizar –>
  14.       <channels>
  15.         <channel ref=“http” port=“1234″ />
  16.         <!– tambien podia haber sido tcp –>
  17.       </channels>
  18.  
  19.     </application>
  20.   </system.runtime.remoting>
  21. </configuration>

Como vemos, es muy simple e intuitivo. Los elementos que más nos interesan son wellknown y channel. Veamos los valores posibles en los atributos del elemento wellknown:

  • mode: <Singleton> | <SingleCall> Con mode le indicamos la forma de compartir nuestra clase.
  • type: <[namespace].[clase], [fichero]> Con type le indicamos es espacio de nombre, la clase que queremos compartir y en que archivo está.
  • objectUri: <nombreQueLeDamosAlServicio> Con objectUri le ponemos un nombre al servicio.

Nota: el uso de los corchetes es para indicar que en ese lugar la escritura es libre, es decir, no tiene valores predeterminados.

Los atributos de los elementos channel podrán tener los siguientes valores:

  • ref: <http> | <tcp> Con ref elegimos el canal.
  • port: <numeroDelPuerto> Con port elegimos el puerto.

2.2. Archivo para el cliente

El archivo del cliente es aún más fácil:

Archivo: Cliente.exe.config

  1. <configuration>
  2.   <system.runtime.remoting>
  3.     <application>
  4.       <client>
  5.         <wellknown
  6.           type=“Calculo.Calculadora, Calculo”
  7.           url=“http://localhost:1234/Calculadora.remota” />
  8.       </client>
  9.     </application>
  10.   </system.runtime.remoting>
  11. </configuration>

Como vemos, en el único elemento que nos debemos fijar es en wellknown, en el que sus atributos pueden coger los siguientes valores:

  • type: <[namespace].[clase], [fichero]> Al igual que antes, la clase que queremos compartir.
  • url: (<http> | <tcp>)://<host>:<puerto>/<nombreQueLeHanDadoAlServicio> La dirección dónde se está compartiendo la clase.

2.3. Los códigos del servidor y del cliente.

El código del servidor se nos reducirá considerablemente:

  1. using System;
  2. using System.Runtime.Remoting;
  3.  
  4. using Calculo;
  5.  
  6. public class Servidor
  7. {
  8.   public static void Main(string [] args)
  9.   {
  10.     // Recogiendo el archivo de configuración del servidor.
  11.     RemotingConfiguration.Configure(“Servidor.exe.config”);
  12.  
  13.     Console.WriteLine(“Atendiendo a las peticiones.”);
  14.     Console.WriteLine(“Pulse ENTER para salir.”);
  15.  
  16.     Console.ReadLine();
  17.   }
  18. }

El código del cliente es igual de fácil que el del servidor (de hecho usan la misma llamada).

  1. using System;
  2. using System.Runtime.Remoting;
  3. using Calculo;
  4.  
  5. public class Cliente
  6. {
  7.   public static void Main (string [] args)
  8.   {
  9.     // Recogiendo el archivo de configuración del cliente.
  10.     RemotingConfiguration.Configure(“Cliente.exe.config”);
  11.  
  12.     // Creando el objeto
  13.     Console.WriteLine(“Creando la calculadora”);
  14.     Calculadora calc = new Calculadora();
  15.  
  16.     // Hacer uso de la calculadora
  17.     /* ….. */
  18.   }
  19. }

Ahora os estaréis preguntando el por qué de no haber dicho esto antes y tener que haber estado modificando el código del cliente y del servidor todo el rato… bueno, hay que aprender todos los métodos.

Indice general de los manuales

  1. Introducción, instalación en Ubuntu y creación de una calculadora.
  2. Modos de compartición de objetos. Creando nuestra primera calculadora distribuida.
    1. Modos de compartición de objetos: Singlecall.
    2. Modos de compartición de objetos: Singleton.
    3. Modos de compartición de objetos: CAO.
  3. Canales: TCP y HTTP. Configuración en archivo XML.  «  [Leyendo]
  4. Uso de interfaces para separar el código entre cliente y servidor.