Sunteți pe pagina 1din 36

Modelos y Arquitecturas Distribuidas

JAVA/RMI
El Modelo de Objetos Distribuidos de
Java
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Introduccin
Java Remote Method Invocation (RMI).
Permite definir e implementar interfaces remotas con este lenguaje.
Sus mtodos se pueden invocar remotamente, de la misma forma
que se invocan las operaciones de interfaces locales.
Solucin de ms alto nivel que el uso directo de sockets o RPCs.
Fcil de desarrollar.
Apropiado para construir sistemas cliente/servidor en redes que sean o
no locales, especialmente si el cliente y el servidor estn escritos en
Java.
RMI tambin puede funcionar sobre IIOP (CORBA).
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Interfaces y Clases en RMI
El soporte para RMI en Java est basado en las interfaces y clases definidas
en los paquetes:
java.rmi . Contiene Clases, Interfases y Excepciones vistas por los
clientes.
java.rmi.server . Contiene Clases, Interfaces y Excepciones vistas por
los servidores.
java.rmi.registry . Contiene Clases, Interfaces y Excepciones tiles
para localizar y registrar objetos remotos.
java.rmi.dgc . Contiene Clases, Interfaces y Excepciones para la
recoleccin de basura.
java.rmi.activation . Contiene Clases, Interfaces y Excepciones para la
activacin de objetos remotos.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Objetivos de RMI
Permitir invocacin remota de mtodos en objetos que residen en
diferentes Mquinas Virtuales.
Permitir invocacin de mtodos remotos por medio de Applets.
Integrar el Modelo de Objetos Distribuidos al lenguaje Java de modo
natural y preservando en lo posible la semntica de objetos en Java.
Permitir la distincin entre objetos locales y remotos.
Mantener la seguridad del ambiente dada por los Security Managers.
Facilitar el desarrollo de aplicaciones distribuidas.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Arquitectura de Java RMI
Objeto Cliente
Stub
Capa de Aplicacin
Referencia
Remota
Transporte
Objeto Servidor
Skeleton
Transporte
Capa de Representantes

Proxy
Capa de RMI
Capa de Protocolo de

Comunicacin (TCP/IP)
Referencia
Remota
Protocolos de Bajo Nivel
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Comunicacin entre el Cliente y el Servidor
Objeto Cliente
Stub
Referencia
Remota
Transporte
Objeto Servidor
Skeleton
Transporte
Referencia
Remota
Protocolos de Bajo Nivel
Solicitud Cliente
Respuesta Servidor
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Arquitectura de Java RMI
Capa de Aplicacin . Objetos que implementan la aplicacin. En general en este nivel
se distinguen dos tipos de agentes: los clientes, que son objetos que invocan mtodos o
hacen peticiones a otros objetos remotos y los servidores, que son objetos que reciben
peticiones de otros objetos remotos.
Capa de Representantes (Proxy) . En esta capa se encuentran los objetos que
actan como representantes locales de objetos remotos. Se encargan del empaquetado y
desempaquetado (marshalling y desmarshalling) de las invocaciones, argumentos y
resultados de mtodos remotos. En RMI existen dos tipos de representantes: los stubs
del lado cliente y los skeletons del lado servidor.
Capa de Referencias Remotas . En esta capa se realiza la interpretacin de las
referencias a objetos remotos, las referencias locales a stubs o skeletons se resuelven a
sus contrapartes remotas y estos datos, junto con los datos "empaquetados" (marshalled)
que contienen las invocaciones o los resultados de invocaciones, se pasan a la Capa de
Transporte.
Capa de Transporte . En esta capa se encuentra el protocolo de comunicacin, que se
encarga de transportar los mensajes que intercambian los distintos objetos. RMI utiliza por
omisin el protocolo TCP/IP.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Caractersticas de Java RMI:
Java extiende su modelo de objetos para tratar con objetos distribuidos.
Misma Sintaxis.
Chequeos de tipos.
El que invoca Mtodos Remotos debe manejar RemoteExceptions.
El objeto Remoto debe implementar la Interfaz Remote.
No necesita de un IDL o LDI (Lenguaje de Definicin de Interfaz).
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Desarrollo de Aplicaciones RMI
Definicin de la
interfaz remota
javac
(.java)
(.java)
usa
Cliente
Ejectuar
Cliente
(.class)
CLIENTE
SERVIDOR
(.class)
Skeleton
(.class)
Implementacin de la
interfaz remota
Stub
(.class)

Servidor
(.class)
Arrancar RMIRegistry
Crear los objetos
Registrar los objetos
javac
rmic
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Aplicacin Genrica:
Servidor:
Crea objeto remoto.
Crea referencia al objeto remoto.
Espera a que un cliente invoque un mtodo en el objeto
remoto.
Cliente:
Obtiene referencia a un objeto remoto en el servidor.
Invoca un mtodo remoto.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Funcionalidades requeridas:
Localizacin de objetos remotos: En RMI se implementa un Registry (registro)
que acta como servidor de nombres y permite la localizacin de objetos remotos
Comunicacin con objetos remotos: A cargo del Sistema RMI, es transparente
para el programador
Paso de parmetros y resultados (objetos locales y remotos) en mtodos
remotos: Incluye el manejo de referencias y la carga dinmica de clases.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Stubs y Skeletons
Stub.
Clase usada por el cliente en sustitucin de la remota.
Implementa la interfaz remota.
La implementacin de cada operacin enva un mensaje a la mquina virtual que
ejecuta el objeto remoto y recibe el resultado.
Los parmetros y el valor de retorno se envan serializados.
En trminos en generales, un stub es un Proxy.
Skeleton.
Clase usada por el servidor
Recibe los mensajes, invoca la operacin del objeto que implementa el interfaz remoto
y enva el resultado al llamador.
En trminos generales, un skeleton es un Adapter
Los Stubs y Skeletons son transparentes al cdigo.
Cuando un cliente invoca una operacin remota que devuelve una referencia a un
objeto remoto, obtiene una instancia del stub correspondiente.
Los stubs y skeletons se generan con el compilador de RMI llamado rmic.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Servicio de nombres
Problema
El servidor crea un objeto que implementa la interfaz, Cmo obtienen los clientes
una referencia a ese objeto ?.
Servicio de nombres.
Permite asociar nombres lgicos (ej.: clock) a objetos
Servidor: asocia un nombre a un objeto
Cliente: obtiene una referencia al objeto a partir del nombre
Objetivo: independencia de ubicacin. En lo posible.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
El servicio de nombres de Java RMI
Java RMI define un servicio de nombres muy sencillo.
El esquema de nombrado sigue la sintaxis de una URL.
//mquina:puerto/nombreDeObjeto, siendo nombreDeObjeto un nombre
simple (ej.: clock).
mquina y puerto hacen referencia a la mquina en la que corre el servicio de
nombres (y no el objeto remoto).
Por defecto, mquina = localhost y puerto = 1099
Interfaz java.rmi.registry.Registry
Permite asociar nombres simples a objetos.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
rmiregistry
Aplicacin que contiene un objeto interfaz
java.rmi.registry.Registry.
Por motivos de seguridad, la implementacin de rmiregistry
prohbe que se invoquen los mtodos bind, rebind y unbind de su
objeto Registry desde otra mquina.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
java.rmi.registry.Registry
public interface Registry extends Remote {
public static final int REGISTRY_PORT = 1099;
public java.rmi.Remote lookup (String name) throws java.rmi.RemoteException,
java.rmi.NotBoundException,
java.rmi.AccessException;
public void bind (String name, Remote obj) throws java.rmi.RemoteException,
java.rmi.AlreadyBoundException, java.rmi.AccessException;
public void unbind (String name) throws java.rmi.RemoteException,
java.rmi.NotBoundException,
java.rmi.AccessException;
public void rebind (String name, Remote obj) throws java.rmi.RemoteException,
java.rmi.AccessException;
public String[] list () throws java.rmi.RemoteException, java.rmi.AccessException;
}
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Registro de Objetos e Invocaciones Remotas
Cliente



Server
registry
RMI
RMI
web server
web server
Protoclo
URL
Protoclo
URL
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Registro de Objetos
Cualquier programa que quiera instanciar un objeto de esta clase debe realizar el
registro con el servicio de nombres de la siguiente forma:

ClaseA a = (ClaseA)Naming.lookup("rmi://"+host+"/"+Nombre");

Antes de arrancar el cliente y el servidor, se debe arrancar el programa rmiregistry en
el servidor para el servicio de nombres.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
java.rmi.Naming
Clase utilidad con mtodos estticos, anlogos a los de
java.rmi.registry.Registry, para registrar/contactar con objetos a partir de una
URL.
Ejemplo:
Clock clock = (Clock) Naming.lookup(//host/clock);
La implementacin de Naming.lookup se contacta con un objeto que
implementa java.rmi.registry.Registry (utilizando la clase utilidad
java.rmi.registry.LocateRegistry), que est en la mquina host,
escuchando por el puerto 1099, e invoca la operacin lookup(clock).

Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
java.rmi.Naming
public final class Naming {
public static Remote lookup (String url) throws RemoteException, NotBoundException,
java.net.MalformedURLException { ... }
public static void bind (String url, Remote obj) throws RemoteException,
AlreadyBoundException,
java.net.MalformedURLException { ... }
public static void unbind (String url) throws RemoteException, NotBoundException,
java.net.MalformedURLException { ... }
public static void rebind (String url, Remote obj) throws RemoteException,
java.net.MalformedURLException { ... }
public static String[] list (String name) throws RemoteException,
java.net.MalformedURLException { ... }
}
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Evaluacin del servicio de nombres de Java RMI
No cumple la propiedad de independencia de ubicacin.
La URL del objeto lleva el nombre y puerto de la mquina en la que corre el
rmiregistry.
Si el rmiregistry cambia de mquina o puerto, es necesario recompilar
los clientes.
Alternativamente, el nombre y puerto se pueden pasar como parmetros
desde la lnea de comandos (como en el ejemplo) o leerlos de un fichero
de configuracin.
An as, es preciso cambiar la configuracin en los clientes.
No permite tener una estructura jerrquica de nombrado (ej.:
/objects/ejemploClock/clock), con posible federacin en servidores.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Poltica Multi-thread
Invocaciones desde distintas mquinas virtuales sobre un mismo
objeto.
Se crea un thread por cada invocacin en el servidor (thread-per-
request).
Invocaciones desde una misma mquina virtual sobre un objeto remoto.
No se garantiza que se cree un thread por cada invocacin en el
servidor.
Conclusin.
La clase que implementa una interfaz remota necesita ser thread-
safe.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Paso de Parmetros a Mtodos Remotos
Hay 3 Mecanismos bsicos (paso de argumentos y resultados).
Tipos primitivos: se pasan por valor (copia). Todos son
serializables.
Objetos Remotos: se pasan por referencia (Stubs, usados para
invocar mtodos remotos).
Objetos Locales: se pasan por valor (solo si son serializables),
se crea un nuevo objeto en la Mquina Virtual que recibe la
copia.
Pedro Rodrguez M.
Ejemplos
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
La interface del Servidor
//package rmi.server;
import java.rmi.*;

public interface MyServer extends Remote {
int getDataNum() throws RemoteException;
String getData(int n) throws RemoteException;
}

grant {
// Allow everything for now permission
java.security.AllPermission;
};
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Interfaces remotas
Una interfaz remota ha de extender, directa o indirectamente, la interfaz
java.rmi.Remote.
Mtodos.
Los tipos de los parmetros y del resultado han de ser serializables.
Han de declarar la excepcin java.rmi.RemoteException (adems de las
propias).
Paso de parmetros.
Los objetos locales se pasan por valor (serializados).
Los objetos remotos se pasan por referencia.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
La Implementacin del Servidor
import java.rmi.*;
import java.rmi.server.*;
import java.rmi.server.UnicastRemoteObject;

public class MyServerImpl extends UnicastRemoteObject implements MyServer {
static String hostName="nico.face.ubiobio.cl:1099";
static String data[] = {"Remote","Method","Invocation,","RMI","de", "Java","es","Maravilloso!"};
public MyServerImpl() throws RemoteException { super(); }
public int getDataNum() throws RemoteException { return data.length; }
public String getData(int n) throws RemoteException { return data[n%data.length]; }
public static void main(String args[]){ System.setSecurityManager(new RMISecurityManager());
try { MyServerImpl instance = new MyServerImpl();
Naming.rebind("rmi://"+hostName+"/MyServer",instance);
System.out.println("Estoy registrado!!");
} catch (Exception ex) { System.out.println(ex); }
}
}
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Implementacin de Unicast Remote Objects
La clase de implementacin extiende java.rmi.server.UnicastRemoteObject e
implementa la interfaz remota.
Para que el objeto puede ser accedido remotamente, necesita ser exportado.
El constructor sin argumentos de UnicastRemoteObject exporta el objeto y
puede lanzar java.rmi.RemoteException.
El constructor (con o sin argumentos) de la clase de implementacin (que
invoca automticamente al constructor sin argumentos de la clase padre)
necesita declarar la excepcin java.rmi.RemoteException.
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Cliente
package rmi.client;
import rmi.server.*;
import java.rmi.*;

public class MyClient {
static String hostName="nico.face.ubiobio.cl:1099";
public static void main(String args[]) {
try {
MyServer server = (MyServer) Naming.lookup("//"+hostName+"/MyServer");
int n = server.getDataNum();
for(int i=0;i < n; ++i ) {
System.out.println(server.getData(i));
}
} catch (Exception ex) {
System.out.println(ex);
}
}
}
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Etapas para construir una aplicacin.
1. Compilar el archivo .java que implementa
la interface:
$ javac MyServer.java

2. Compilar el servidor que implementa la
interface:
$ javac MyServerImpl.java

3. Generar el stub y el skeleton con:
$ rmic MyServerImpl

4. Registrar el servidor:
$ rmiregistry & //dejarlo en background

5. Ejecutar el servidor y registrarlo:
$ java -Djava.security.policy=policy.all
MyServerImpl .
1. Compilar el archivo .java que
implementa la interface:
$ javac MyServer.java

2. Compilar el cliente:

$ javac MyCliente.java

2. Ejecutar el cliente:

$ java MyCliente


Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Serializacin de Objetos
RMI soporta objetos por valor y por referencia.
Los objetos por referencia son exportado por RMIRegistry.
RMYRegistry es un servicio ejecutado como proceso demonio.
Objetos por valor es posible con la librera de serializacin.
Un objeto serializable es un objeto que se puede convertir en una secuencia de bytes.
Para que un objeto sea serializable, debe implementar la interfaz java.io.Serializable.
Los objetos serializables son posteriormente reconstruidos.
Cuando se lleva un objeto serializable de una mquina a otra, ste se serializa y una vez en
la mquina husped, se reconstruye y se usa.
Ventajas del paso por valor:
Minimiza el trfico en la red.
Las comunicaciones con ese objeto son locales.
Cuando se realiza una invocacin remota:
(Local) El objeto se serializa y se enva al objeto remoto como una secuencia de bytes.
(Remoto) Se obtiene el objeto original a partir de la secuencia de bytes.
(Remoto) Se ejecuta el mtodo y se obtiene un valor de retorno.
(Remoto) El valor de retorno se serializa y se enva como una secuencia de bytes.
(Local) Se obtiene el retorno a partir de la secuencia de bytes
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Almacenamiento de objetos en Archivos
public class SerialApp {
public static void main( Strign args[] ) {
try {
ObjectOutputStream outputStream = new ObjectOutputStream(new
FileOutputStream(temp));
Properties prop = System.getProperties();
outputStream.writeObject(prop);
outputStream.close();
ObjectInputStream inputStream = new ObjectInputStream(new
FileInputStream(temp));
Properties newProp = (Properties)inputStream.readObject();
inputStream.close();
newProp.list(System.out);
} catch(Exception ex) { System.out.println(ex.toString()); }
}
}

Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Objetos por Valor: Definiendo la interface y la clase
Serializable
public interface Clock extends Remote {
public TimeOfDay getTimeOfDay() throws RemoteException;
}

public class TimeOfDay implements Serializable {
private int hour;
private int minute;
private int second;

public TimeOfDay(int hour, int minute, int second) {
this.hour = hour;
this.minute = minute;
this.second = second;
}
}
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
Implementacin de la clase Clock
class ClockImpl extends UnicastRemoteObject implements Clock {
ClockImpl() throws RemoteException {}

public TimeOfDay getTimeOfDay() {
int hour = Calendar.getInstance().get(Calendar.HOUR);
int minute = Calendar.getInstance().get(Calendar.MINUTE);
int second = Calendar.getInstance().get(Calendar.SECOND);

return new TimeOfDay(hour, minute, second);
}
}
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
El Servidor
class Server {
public static void main (String[] args) {
//Instalar RMI security manager.
System.setSecurityManager(new RMISecurityManager());
//Crear una instancia de "ClockImpl", y lo registra en el RMI registry.
try {
ClockImpl clock = new ClockImpl();
Naming.rebind("clock", clock);
System.out.println("Server is working ...");
} catch (Exception e) {
e.printStackTrace();
}
}
}
Pedro Rodrguez M.
Sistemas Distribuidos Orientados
a Objetos
El Cliente
class Client {
public static void main (String[] args) {
//Conseguir direccin de registro de RMI, el cual puede ser especificado
como "hostName[:port]".
String registryAddress;
if (args.length == 0) registryAddress = "localhost";
else registryAddress = args[0];
try { // Instala RMI security manager.
System.setSecurityManager(new RMISecurityManager());
//Obtiene una referencia a la implementacin del objeto "Clock".
String clockURL = "//" + registryAddress + "/clock";
Clock clock = (Clock) Naming.lookup(clockURL);
//Obtiene la hora del da y la imprime.
TimeOfDay timeOfDay = clock.getTimeOfDay();
System.out.println("Time of day: " + timeOfDay);
} catch (Exception e) {
e.printStackTrace();
}
}
}

S-ar putea să vă placă și