Muestra las diferencias entre dos versiones de la página.
| Próxima revisión | Revisión previa | ||
| dad:rmi [2023/11/27 12:03] – creado thejuanvisu | dad:rmi [2024/01/06 20:35] (actual) – [Unable to make public abstract boolean] thejuanvisu | ||
|---|---|---|---|
| Línea 4: | Línea 4: | ||
| * Los datos se pasan como argumentos del método.7 | * Los datos se pasan como argumentos del método.7 | ||
| + | ===== Diferencias con la programación local ===== | ||
| - | Definicion de objetos | + | * Definicion de objetos |
| - | Locales: definidos por una clase | + | |
| - | Remotos: Comportamiento definido por una interface que extiende java.rmi.remote | + | |
| - | + | | |
| - | Implementación de ojetos | + | |
| - | Locales: implementados por su clase | + | |
| - | Remotos: comportamiento ejecutado por una clase que implementa la interfaz | + | |
| - | + | | |
| - | Creación de objetos | + | |
| - | Locales: Instancias se crean con new | + | |
| - | Remotos: instancias creadas en el servidor con un new, el cliente no puede crear objetos | + | |
| - | + | | |
| - | Acceso a objetos: | + | |
| - | Locales: a través de referencia local | + | |
| - | Remoto: | + | * Remotos: referencia al proxy que sabe como conectar con el objeto remoto |
| - | + | * Referencias activas: | |
| - | Referencias: | + | * Locales: si es apuntada por al menos un objeto |
| - | Locales: una referencia a un objeto | + | * Remoto: activo mientras sus servicios sean solicitados durante un período de tiempo |
| + | * Recolector de basura: | ||
| + | * Locales: Recogido si no está activo | ||
| + | * Remotos: Recogido si no hay referencias locales ni está siendo utilizado por clientes externos | ||
| + | * Excepciones: | ||
| + | * Locales: RunTimeExceptions Y Exceptions | ||
| + | * Remotos: RemoteException | ||
| ===== Arquitectura ===== | ===== Arquitectura ===== | ||
| Línea 35: | Línea 42: | ||
| * Capa de transporte: Permite la conectividad entre objetos basada en TCP/IP. | * Capa de transporte: Permite la conectividad entre objetos basada en TCP/IP. | ||
| - | {{drawio> | + | {{drawio> |
| + | |||
| + | ==== Servicio de Nombres ==== | ||
| + | * JNDI (Java Naming Directory Interface) | ||
| + | * Busca los objetos de java remotos por su nombre | ||
| + | * No se limita solo a RMI | ||
| + | * RMIRegistry | ||
| + | * El servidor registra un objeto y lo hace accesible a los clientes | ||
| + | * Corre en máquinas donde estén los servidores | ||
| + | * Puerto por defecto: 1099 | ||
| + | |||
| + | ==== Como Buscar ==== | ||
| + | * El cliente debe buscar el servicio: | ||
| + | * java.rmi.Naming.lookup(RMIUrl) | ||
| + | * Una URL en versión RMI sería: | ||
| + | |||
| + | < | ||
| + | rmi://< | ||
| + | </ | ||
| ===== Distribución de clases ===== | ===== Distribución de clases ===== | ||
| Línea 46: | Línea 71: | ||
| * Interface | * Interface | ||
| * Stubs | * Stubs | ||
| + | |||
| + | ===== Implementación Servidor ===== | ||
| + | En este ejemplo implementaremos una calculadora en un servidor que será utilizada por un cliente. | ||
| + | ==== Interfaz Servidor ==== | ||
| + | La interfaz debe heredar de java.rmi.Remote | ||
| + | <code java InterfazSertvidor.jar> | ||
| + | public interface InterfazServidor extends java.rmi.Remote{ | ||
| + | public long sumar(long a, long b) | ||
| + | throws java.rm.RemoteException; | ||
| + | | ||
| + | public long restar (long a, long b) | ||
| + | throws java.rm.RemoteException; | ||
| + | | ||
| + | public long multiplicar () | ||
| + | throws java.rmi.RemoteException; | ||
| + | |||
| + | public long dividir() | ||
| + | throws java.rmi.RemoteException; | ||
| + | | ||
| + | } | ||
| + | </ | ||
| + | |||
| + | ==== Implementación Servidor ==== | ||
| + | |||
| + | Aquí implementaremos las funciones de la interfaz del servidor. Se debe heredar de UnicastRemoteObject con un Extends e indicar que se va a implementar la interface anterior con Implements: | ||
| + | |||
| + | <code java ImplementacionInterfaceServidor.jar> | ||
| + | |||
| + | public class ImplementacionInterfaceServidor extends UnicastRemoteObject implements InterfazServidor{ | ||
| + | private static final long serialVersionUID = 1L; | ||
| + | | ||
| + | public implementacion() throws RemoteException{ | ||
| + | super(); | ||
| + | } | ||
| + | | ||
| + | public long sumar(long a, long b) throws RemoteException{ | ||
| + | return a+b; | ||
| + | } | ||
| + | | ||
| + | public long restar(long a, long b) throws RemoteException{ | ||
| + | return a-b; | ||
| + | } | ||
| + | | ||
| + | public long multiplicar (long a, long b) throws RemoteException{ | ||
| + | return a*b; | ||
| + | } | ||
| + | | ||
| + | public long dividir (long a, long b) throws RemoteExcepcion{ | ||
| + | return a/b; | ||
| + | } | ||
| + | | ||
| + | } | ||
| + | |||
| + | </ | ||
| + | |||
| + | ==== Implementación servidor ==== | ||
| + | |||
| + | <code java Server.jar> | ||
| + | |||
| + | public class Server(){ | ||
| + | public server(){ | ||
| + | try{ | ||
| + | | ||
| + | //creamos el servicio en el puerto 1099 | ||
| + | LocateRegistry.createRegistry(1099); | ||
| + | //creamos un nuevo objeto con la funcionalidad | ||
| + | InterfazServidor is = new ImplementacionInterfaceServidor(); | ||
| + | // | ||
| + | //Ejemplo de URL(" | ||
| + | Naming.rebind(" | ||
| + | | ||
| + | }catch (Exception e){ | ||
| + | System.out.println(" | ||
| + | } | ||
| + | } | ||
| + | | ||
| + | public static void main(String args[]){ | ||
| + | new Server(); | ||
| + | } | ||
| + | | ||
| + | } | ||
| + | |||
| + | </ | ||
| + | |||
| + | ===== Implementación Cliente ===== | ||
| + | <code java Client.jar> | ||
| + | |||
| + | public class Client{ | ||
| + | public static void main(String[] args){ | ||
| + | try{ | ||
| + | //Con Naminglookup(URL del RMI) el cliente busca el servicio | ||
| + | //Formato de la URL: RMI:// | ||
| + | InterfazServidor is = (InterfazServidor)Naming.lookup(" | ||
| + | | ||
| + | System.out.println(is.sumar(3, | ||
| + | System.out.println(is.restar(7, | ||
| + | System.out.println(is.multiplicar(8, | ||
| + | System.out.println(is.dividir(4, | ||
| + | }catch(Exception e){ | ||
| + | System.out.println(" | ||
| + | e.printStackTrace(); | ||
| + | } | ||
| + | | ||
| + | } | ||
| + | } | ||
| + | |||
| + | </ | ||
| + | |||
| + | ===== Soluciones a Errores comunes ===== | ||
| + | ==== Unable to make public abstract boolean ==== | ||
| + | En el archivo module-info.java debemos revisar que se esté exportando el paquete | ||
| + | <code java module-info.java> | ||
| + | module nombre_proyecto { | ||
| + | exports nombre_paquete; | ||
| + | } | ||
| + | |||
| + | </ | ||