Java Language RMI via JNDI


Exemple

Cet exemple montre comment JNDI fonctionne dans RMI. Il a deux rôles:

  • fournir au serveur une API bind / unbind / rebind au registre RMI
  • fournir au client une API de recherche / liste au registre RMI.

Le registre RMI fait partie de RMI, pas de JNDI.

Pour simplifier, nous utiliserons java.rmi.registry.CreateRegistry() pour créer le registre RMI.

  1. Server.java (le serveur JNDI)

    package com.neohope.jndi.test;
    
    import javax.naming.Context;
    import javax.naming.InitialContext;
    import javax.naming.NamingException;
    import java.io.IOException;
    import java.rmi.RemoteException;
    import java.rmi.registry.LocateRegistry;
    import java.util.Hashtable;
    
    /**
     * JNDI Server
     * 1.create a registry on port 1234
     * 2.bind JNDI
     * 3.wait for connection
     * 4.clean up and end
     */
    public class Server {
        private static Registry registry;
        private static InitialContext ctx;
    
        public static void initJNDI() {
            try {
                registry = LocateRegistry.createRegistry(1234);
                final Hashtable jndiProperties = new Hashtable();
                jndiProperties.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.rmi.registry.RegistryContextFactory");
                jndiProperties.put(Context.PROVIDER_URL, "rmi://localhost:1234");
                ctx = new InitialContext(jndiProperties);
            } catch (NamingException e) {
                e.printStackTrace();
            } catch (RemoteException e) {
                e.printStackTrace();
            }
        }
    
        public static void bindJNDI(String name, Object obj) throws NamingException {
            ctx.bind(name, obj);
        }
    
        public static void unbindJNDI(String name) throws NamingException {
            ctx.unbind(name);
        }
    
        public static void unInitJNDI() throws NamingException {
            ctx.close();
        }
    
        public static void main(String[] args) throws NamingException, IOException {
            initJNDI();
            NMessage msg = new NMessage("Just A Message");
            bindJNDI("/neohope/jndi/test01", msg);
            System.in.read();
            unbindJNDI("/neohope/jndi/test01");
            unInitJNDI();
        }
    }
    
  2. Client.java (le client JNDI)

    package com.neohope.jndi.test;
    
    import javax.naming.Context;
    import javax.naming.InitialContext;
    import javax.naming.NamingException;
    import java.util.Hashtable;
    
    /**
     * 1.init context
     * 2.lookup registry for the service
     * 3.use the service
     * 4.end
     */
    public class Client {
        public static void main(String[] args) throws NamingException {
            final Hashtable jndiProperties = new Hashtable();
            jndiProperties.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.rmi.registry.RegistryContextFactory");
            jndiProperties.put(Context.PROVIDER_URL, "rmi://localhost:1234");
    
            InitialContext ctx = new InitialContext(jndiProperties);
            NMessage msg = (NeoMessage) ctx.lookup("/neohope/jndi/test01");
            System.out.println(msg.message);
            ctx.close();
        }
    }
    
  3. NMessage.java (classe de serveur RMI)

    package com.neohope.jndi.test;
    
    import java.io.Serializable;
    import java.rmi.Remote;
    
    /**
     * NMessage
     * RMI server class
     * must implements Remote and Serializable 
     */
    public class NMessage implements Remote, Serializable {
        public String message = "";
    
        public NMessage(String message)
        {
            this.message = message;
        }
    }
    

Comment exécuter le programme:

  1. construire et démarrer le serveur
  2. construire et démarrer le client

Présenter

Modèle JNDI

L' interface JNDI (Java Naming and Directory Interface) est une API Java pour un service d'annuaire qui permet aux clients de logiciels Java de découvrir et de rechercher des données et des objets via un nom. Il est conçu pour être indépendant de toute implémentation de service d'annuaire ou de nom spécifique.

L'architecture JNDI se compose d'une API (interface de programmation d'application) et d'une interface SPI (Service Provider Interface). Les applications Java utilisent cette API pour accéder à divers services de noms et de répertoires. Le SPI permet de brancher de manière transparente divers services de noms et de répertoires, ce qui permet à l'application Java utilisant l'API de la technologie JNDI d'accéder à leurs services.

Comme vous pouvez le voir ci-dessus, JNDI prend en charge LDAP, DNS, NIS, NDS, RMI et CORBA. Bien sûr, vous pouvez l'étendre.

Comment ça marche

Dans cet exemple, l'interface RMI Java utilise l'API JNDI pour rechercher des objets dans un réseau. Si vous voulez rechercher un objet, vous avez besoin d'au moins deux informations:

  • Où trouver l'objet

Le registre RMI gère les liaisons de noms, il vous indique où trouver l'objet.

  • Le nom de l'objet

Quel est le nom d'un objet? C'est généralement une chaîne, il peut également s'agir d'un objet qui implémente l'interface Name.

Pas à pas

  1. Tout d'abord, vous avez besoin d'un registre qui gère la liaison de noms. Dans cet exemple, nous utilisons java.rmi.registry.LocateRegistry .

    //This will start a registry on localhost, port 1234
    registry = LocateRegistry.createRegistry(1234);
    
  2. Le client et le serveur ont tous deux besoin d'un contexte. Le serveur utilise le contexte pour lier le nom et l'objet. Le client utilise le contexte pour rechercher le nom et obtenir l'objet.

    //We use com.sun.jndi.rmi.registry.RegistryContextFactory as the InitialContextFactory
    final Hashtable jndiProperties = new Hashtable();
    jndiProperties.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.rmi.registry.RegistryContextFactory");
    //the registry usrl is "rmi://localhost:1234"
    jndiProperties.put(Context.PROVIDER_URL, "rmi://localhost:1234");
    InitialContext ctx = new InitialContext(jndiProperties);
    
  3. Le serveur lie le nom et l'objet

    //The jndi name is "/neohope/jndi/test01"
    bindJNDI("/neohope/jndi/test01", msg);
    
  4. Le client recherche l'objet par le nom "/ neohope / jndi / test01"

    //look up the object by name "java:com/neohope/jndi/test01"
    NeoMessage msg = (NeoMessage) ctx.lookup("/neohope/jndi/test01");
    
  5. Maintenant, le client peut utiliser l'objet

  6. Lorsque le serveur se termine, vous devez nettoyer.

    ctx.unbind("/neohope/jndi/test01");
    ctx.close();