20 Jini Lookup Service
The JMX API defines three bindings to lookup services, using existing lookup
technologies This examples provide a sample implementation of the Jini Lookup Service.
The source code contained in this section is used to create corresponding files in the
examples/
directory specified in the appropriate setup procedure
and includes:
-
README file
-
Server
-
Client
-
java.policy
-
jini.properties.template
examples/Lookup/jini/README
/*
* Copyright (c) 2004, 2019 Oracle and/or its affiliates. All rights reserved.
* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*/
# ==============================================================================
#
# Example of using Jini as Lookup service - registering and looking up
# an RMI Connector (IIOP/JRMP)
#
# ==============================================================================
#
# Requirements:
#
# Before running this example you will have to:
# ---------------------------------------------
#
# Get and install Jini:
#
# http://www.jini.org/
# http://jini.dev.java.net/
# http://starterkit.dev.java.net/downloads/index.html
#
# This example has been implemented using the Jini Technology Starter Kit
# Version 1.2.1_002.
#
# If you wish to use an external directory for the RMI JMX Connectors
# (URLs of the form jmx:service:[rmi|iiop]:/host:port/jndi/jndi-url)
# then:
#
# o If you wish to use rmiregistry in conjunction with the RMI/JRMP
# JMX Connector you will have to start a rmiregistry (see below).
#
# o If you wish to use CORBA Naming Service in conjunction with the RMI/IIOP
# JMX Connector you will have to start an ORB daemon (see below).
#
# o If you wish to use LDAP in conjunction with the RMI JMX Connectors
# you will have to install/setup a directory server
#
# In order to compile and run the example, make a copy of this README file, and
# then simply cut and paste all the commands as needed into a terminal window.
#
# This README makes the assumption that you are running under Java SE 6 on Unix,
# you are familiar with Jini, the JMX technology, with LDAP and JNDI, and with
# the bourne shell or korn shell syntax.
#
# All the commands below are defined using Unix korn shell syntax.
#
# If you are not running Unix and korn shell you are expected to be able to
# adapt these commands to your favorite OS and shell environment.
#
# Update & define the following variables to match your local installation:
#
JINI_HOME=@INSTALL_HOME_FOR_JINI@
# Define the following variables:
#
JINILIB=$JINI_HOME/lib
classp=$JINILIB/jini-core.jar:$JINILIB/jini-ext.jar
# Create a jini.properties file, either from
# $JINI_HOME/example/launcher/jini12_<platform>.properties
# or from the jini.properties.template file
# provided in this example for the Unix platform.
# Replace the paths and hostnames (default is localhost) where needed in the
# jini.properties file.
# Launch Jini StartService example:
#
java -classpath $JINILIB/jini-examples.jar com.sun.jini.example.launcher.StartService &
# Load the edited jini.properties file in the launcher tool.
# Use Jini StartService example to start:
# * RMID,
# * WebServer,
# * Reggie,
# * and LookupBrowser
#-------------------------------------------------------------------------------
# Start an rmiregistry
#
rmiregistry 9999 &
#-------------------------------------------------------------------------------
# Start an ORB daemon:
#
rm -rf ./orb.db
orbd -ORBInitialPort 7777 &
#-------------------------------------------------------------------------------
# Start an LDAP Server, and create a new dc=Test suffix inside.
#
# (only needed if you wish to register the RMI or IIOP
# stubs in LDAP, instead of using CORBA Naming Service or RMI registry)
#
# You will have
# to make sure the Java Schema (RFC 2713:
# http://www.ietf.org/rfc/rfc2713.txt) is known by that server
#-------------------------------------------------------------------------------
# Compile Server.java and Client.java
#
# * Server.java: creates an MBeanServer, creates and starts an
# RMI connector (JRMP/IIOP)
# * Client.java: lookup a connector in Jini
# list all MBeans.
javac -d . -classpath $classp Server.java Client.java
#-------------------------------------------------------------------------------
# LDAP parameters:
# Supply the appropriate hostname below, and define this variable:
#
ldaphost=gigondas
# Supply the appropriate port number below, and define this variable:
#
ldapport=6666
# Supply the appropriate principal below, and define this variable:
#
principal="cn=Directory Manager"
# Supply the appropriate credentials below, and define this variable:
#
credentials=
#-------------------------------------------------------------------------------
# JNDI URLs
#
jndirmi="rmi://localhost:9999"
jndiiiop="iiop://localhost:7777"
jndildap="ldap://$ldaphost:$ldapport"
#-------------------------------------------------------------------------------
# JMX Service URLs
#
jmxiiopurl="service:jmx:iiop:///jndi/${jndiiiop}/server"
jmxrmiurl="service:jmx:rmi:///jndi/${jndirmi}/server"
jmxiiopldapurl="service:jmx:iiop:///jndi/${jndildap}/cn=x,dc=Test"
jmxrmildapurl="service:jmx:rmi:///jndi/${jndildap}/cn=x,dc=Test"
jmxstuburl="service:jmx:rmi://"
jmxiorurl="service:jmx:iiop://"
#-------------------------------------------------------------------------------
# Below we illustrate the different JMX Connector Servers
# which you have the choice to start.
# There are seven cases labelled (a) to (f):
#
# * RMI Connectors
# + over JRMP
# - without any external directory (a)
# - using rmiregistry as external directory (b)
# - using LDAP as external directory (c)
# + over IIOP
# - without any external directory (d)
# - using CORBA Naming Service as external directory (e)
# - using LDAP as external directory (f)
# NOTE-1: As defined in section 6.1 "Terminology" of the "JMX Remote API 1.0
# Specification" document, an agent is composed of one MBean Server and of
# one or more Connector Servers. There can be several agents running in one JVM.
# For flexibility of this example, the jini.Server class creates an agent which
# is composed of one MBean Server and of only one Connector Server. The class
# jini.Server decides which type of Connector Server to create depending on the
# value given to the "url" system property when you start the example.
# NOTE-2: The value of the "agent.name" system property is the value that the
# jini.Server class will give to the "AgentName" lookup attribute when it
# registers the connector's URL in the lookup service. As defined in Table 6.1
# "Lookup attributes for connectors" of the "JMX Remote API 1.0 Specification"
# document: the "AgentName" lookup attribute is a simple name used to identify
# the *AGENT* to which the connector is attached. It makes it possible to
# search, with a query to the lookup service, for all the connectors registered
# by a given agent.
# (a) You can start an agent with an RMI Connector Server over JRMP
# without using any external directory
#
java -classpath .:$classp -Ddebug=true \
-Dagent.name=test-server-a \
-Durl="service:jmx:rmi://" \
-Djava.security.policy=java.policy \
jini.Server &
# (b) Or you can start an agent with an RMI Connector Server over JRMP
# using rmiregistry as external directory
# (Start rmiregistry first, if not yet started)
#
java -classpath .:$classp -Ddebug=true \
-Dagent.name=test-server-b \
-Durl="service:jmx:rmi:///jndi/${jndirmi}/server" \
-Djava.security.policy=java.policy \
jini.Server &
# (c) Or you can start an agent with an RMI Connector Server over JRMP
# using LDAP as external directory
# (First start an LDAP server and create the dc=Test suffix)
#
java -classpath .:$classp -Ddebug=true \
-Dagent.name=test-server-c \
-Durl="service:jmx:rmi:///jndi/${jndildap}/cn=x,dc=Test" \
-Djava.security.policy=java.policy \
-Djava.naming.security.principal="$principal" \
-Djava.naming.security.credentials="$credentials" \
jini.Server &
# (d) Or you can start an agent with an RMI Connector Server over IIOP
# without using any external directory
#
java -classpath .:$classp -Ddebug=true \
-Dagent.name=test-server-d \
-Durl="service:jmx:iiop://" \
-Djava.security.policy=java.policy \
jini.Server &
# (e) Or you can start an agent with an RMI Connector Server over IIOP
# using CORBA Naming Service as external directory
# (Start ORBD first if not yet started).
#
java -classpath .:$classp -Ddebug=true \
-Dagent.name=test-server-e \
-Durl="service:jmx:iiop:///jndi/${jndiiiop}/server" \
-Djava.security.policy=java.policy \
jini.Server &
# (f) Or you can start an agent with an RMI Connector Server over IIOP
# using LDAP as external directory
# (First start an LDAP server and create the dc=Test suffix)
#
java -classpath .:$classp -Ddebug=true \
-Dagent.name=test-server-f \
-Durl="service:jmx:iiop:///jndi/${jndildap}/cn=x,dc=Test" \
-Djava.security.policy=java.policy \
-Djava.naming.security.principal="$principal" \
-Djava.naming.security.credentials="$credentials" \
jini.Server &
# Once you have started one or more agents, you can start the Client.
#
java -classpath .:$classp -Ddebug=true \
-Djava.security.policy=java.policy \
jini.Client
#-------------------------------------------------------------------------------
examples/Lookup/jini/Server.java
/*
* Copyright (c) 2004, Oracle and/or its affiliates. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* - Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* - Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* - Neither the name of Oracle or the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package jini;
import net.jini.core.lookup.ServiceRegistrar;
import net.jini.admin.Administrable;
import net.jini.core.discovery.LookupLocator;
import net.jini.core.lookup.ServiceItem;
import net.jini.core.lookup.ServiceRegistration;
import net.jini.core.entry.Entry;
import net.jini.core.lease.Lease;
import net.jini.core.lookup.ServiceTemplate;
import net.jini.core.lookup.ServiceMatches;
import javax.management.remote.*;
import javax.management.remote.rmi.*;
import javax.management.*;
import java.util.Map;
import java.util.List;
import java.util.HashMap;
import java.util.Hashtable;
import java.util.ArrayList;
import java.io.IOException;
import java.net.MalformedURLException;
import java.io.Serializable;
import java.rmi.RMISecurityManager;
import javax.naming.Context;
/**
* This class demonstrates how to use Jini as a lookup service for
* JSR 160 connectors. It shows how to register a JMXConnectorServer
* with the Jini lookup service.
* <p>
* See README file and {@link #main(String[])} for more details.
* <p>
* Make sure to read the section "Binding with Lookup Services" of
* the JMX Remote API 1.0 Specification before looking at this example.
*/
public class Server {
/**
* The local MBeanServer.
*/
private final MBeanServer mbs;
private static boolean debug = false;
/**
* Constructs a Server object. Creates a new MBeanServer.
*/
public Server() {
mbs = MBeanServerFactory.createMBeanServer();
}
/**
* Creates an RMI Connector Server, starts it, and registers it
* with the Jini Lookup Service.
* <p>
* This method will transfer a fixed set of System Properties to
* the Map given to the RMIConnectorServer constructor. Some
* JNDI properties, if defined, are transfered to the Map so
* that they may be used when LDAP is used as external directory
* to register the RMI Stub (see {@link javax.management.remote.rmi}
* Javadoc). Note that even if LDAP is used as external directory
* the {@link Context#INITIAL_CONTEXT_FACTORY
* Context.INITIAL_CONTEXT_FACTORY} and
* {@link Context#PROVIDER_URL Context.PROVIDER_URL} properties
* usually don't need to be passed.
* <p>
* The following System properties, if defined, are transfered to
* the Map given to the RMIConnectorServer constructor.
* <ul><li>{@link Context#INITIAL_CONTEXT_FACTORY
* Context.INITIAL_CONTEXT_FACTORY}</li>
* <li>{@link Context#PROVIDER_URL
* Context.PROVIDER_URL}</li>
* <li>{@link Context#SECURITY_PRINCIPAL
* Context.SECURITY_PRINCIPAL}</li>
* <li>{@link Context#SECURITY_CREDENTIALS
* Context.SECURITY_CREDENTIALS}</li>
* <li>{@link RMIConnectorServer#JNDI_REBIND_ATTRIBUTE
* RMIConnectorServer.JNDI_REBIND_ATTRIBUTE} - default
* is <code>true</code>.</li>
* </ul>
*
* @param url A string representation of the JMXServiceURL.
*
* @return the created RMIConnectorServer.
*/
public JMXConnectorServer rmi(String url)
throws IOException, JMException, ClassNotFoundException {
// Make a JMXServiceURL from the url string.
//
JMXServiceURL jurl = new JMXServiceURL(url);
// Prepare the environment Map
//
final HashMap env = new HashMap();
final String rprop = RMIConnectorServer.JNDI_REBIND_ATTRIBUTE;
final String rebind=System.getProperty(rprop,"true");
final String factory =
System.getProperty(Context.INITIAL_CONTEXT_FACTORY);
final String ldapServerUrl =
System.getProperty(Context.PROVIDER_URL);
final String ldapUser =
System.getProperty(Context.SECURITY_PRINCIPAL);
final String ldapPasswd =
System.getProperty(Context.SECURITY_CREDENTIALS);
// Transfer some system properties to the Map
//
if (factory!= null) // this should not be needed
env.put(Context.INITIAL_CONTEXT_FACTORY,factory);
if (ldapServerUrl!=null) // this should not be needed
env.put(Context.PROVIDER_URL, ldapServerUrl);
if (ldapUser!=null) // this is needed when LDAP is used
env.put(Context.SECURITY_PRINCIPAL, ldapUser);
if (ldapPasswd != null) // this is needed when LDAP is used
env.put(Context.SECURITY_CREDENTIALS, ldapPasswd);
env.put(rprop,rebind); // default is true.
// Create an RMIConnectorServer
//
System.out.println("Creating RMI Connector: " + jurl);
JMXConnectorServer rmis =
JMXConnectorServerFactory.newJMXConnectorServer(jurl, env, mbs);
// Get the AgentName for registering the Connector in the Lookup Service
//
final String agentName = System.getProperty("agent.name",
"DefaultAgent");
// Start the connector and register it with Jini Lookup Service.
//
start(rmis,env,agentName);
return rmis;
}
/**
* Start a JMXConnectorServer and register it with Jini Lookup Service.
*
* @param server the JMXConnectorServer to start and register.
* @param env the environment Map.
* @param agentName the AgentName with which the proxy must be registered
* in the Jini Lookup Service.
*/
public void start(JMXConnectorServer server, Map env, String agentName)
throws IOException, ClassNotFoundException {
// Start the JMXConnectorServer
//
server.start();
// Get a pointer to Jini Lookup Service
//
final ServiceRegistrar registrar = getRegistrar();
// Create a JMXConnector proxy to register with Jini
//
final JMXConnector proxy = server.toJMXConnector(env);
// Register the proxy with Jini Lookup Service.
//
register(registrar,proxy,agentName);
}
/**
* Get a pointer to the Jini Lookup Service.
* (See Jini documentation for more info).
* <p>
* The Jini Lookup Service URL is determined as follows:
* <p>
* If the System property <code>"jini.lookup.url"</code> is provided,
* its value is the Jini Lookup Service URL.
* <p>
* Otherwise, the default URL is assumed to be
* <code>"jini://localhost"</code>
* @return a pointer to the Jini Lookup Service.
*/
public static ServiceRegistrar getRegistrar()
throws IOException, ClassNotFoundException, MalformedURLException {
final String jurl =
System.getProperty("jini.lookup.url","jini://localhost");
final LookupLocator lookup = new LookupLocator(jurl);
final ServiceRegistrar registrar = lookup.getRegistrar();
if (registrar instanceof Administrable)
debug("Registry is administrable.");
return registrar;
}
/**
* Register a JMXConnector proxy with the Jini Lookup Service.
*
* @param registrar A pointer to the Jini Lookup Service, as returned
* by {@link #getRegistrar()}.
* @param proxy A JMXConnector server proxy, that should have
* been obtained from
* {@link JMXConnectorServer#toJMXConnector(Map)
* JMXConnectorServer.toJMXConnector(Map)};
* @param name The AgentName with which the proxy must be registered
* in the Jini Lookup Service.
*
* @return The ServiceRegistration object returned by the Jini Lookup
* Service.
*/
public static ServiceRegistration register(ServiceRegistrar registrar,
JMXConnector proxy, String name)
throws IOException {
// Prepare Service's attributes entry
//
Entry[] serviceAttrs = new Entry[] {
new net.jini.lookup.entry.Name(name)
// Add here the lookup attributes you want to specify.
};
System.out.println("Registering proxy: AgentName=" + name );
debug("\t\t" + proxy);
// Create a ServiceItem from the service instance
//
ServiceItem srvcItem = new ServiceItem(null, proxy, serviceAttrs);
// Register the Service with the Lookup Service
//
ServiceRegistration srvcRegistration =
registrar.register(srvcItem, Lease.ANY);
debug("Registered ServiceID: " +
srvcRegistration.getServiceID().toString());
return srvcRegistration;
}
/**
* Trace a debug message.
*/
private static void debug(String msg) {
if (debug) System.out.println(msg);
}
/**
* Program Main
* <p>
* Creates a server object, gets the JMX Service URL, and calls
* the method that will create and register the appropriate
* JMX Connector Server for that URL.
* <p>
* You may wish to use the following properties on the Java command line:
* <ul>
* <li><code>-Durl=<jmxServiceURL></code>: specifies the URL of
* the JMX Connector Server you wish to use. See README file for more
* details</li>
* <li><code>-Dagent.name=<AgentName></code>: specifies an
* AgentName to register with.</li>
* <li><code>-Djini.lookup.url=<jini-url></code>:
* the Jini Lookup Service URL (default is "jini://localhost"),
* see {@link #getRegistrar()}.</li>
* <li><code>-Ddebug="true|false"</code>: switch the Server debug flag
* on/off (default is "false").</li>
* </ul>
*/
public static void main(String[] args) {
try {
// Jini requires a security manager.
//
if (System.getSecurityManager() == null)
System.setSecurityManager(new RMISecurityManager());
// Get the value of the debug flag.
//
debug = (Boolean.valueOf(System.getProperty("debug","false"))).
booleanValue();
// Create a new Server object.
//
final Server s = new Server();
// Get the JMXConnector URL
//
final String url = System.getProperty("url", "service:jmx:rmi://");
// Build a JMXServiceURL
//
final JMXServiceURL jurl = new JMXServiceURL(url);
// Creates a JMX Connector Server
//
debug("Creating Connector: " + jurl);
final String p = jurl.getProtocol();
if (p.equals("rmi")) // Create an RMI Connector
s.rmi(url);
else if (p.equals("iiop")) // Create an RMI/IIOP Connector
s.rmi(url);
else // Unsupported protocol
throw new MalformedURLException("Unsupported protocol: " + p);
System.out.println("\nService URL successfully registered " +
"in the Jini Lookup Service");
} catch (Exception x) {
// Something went wrong somewhere....
//
System.err.println("Unexpected exception caught in main: " + x);
x.printStackTrace(System.err);
}
}
}
examples/Lookup/jini/Client.java
/*
* Copyright (c) 2004, Oracle and/or its affiliates. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* - Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* - Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* - Neither the name of Oracle or the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package jini;
import net.jini.core.lookup.ServiceRegistrar;
import net.jini.admin.Administrable;
import net.jini.core.discovery.LookupLocator;
import net.jini.core.lookup.ServiceItem;
import net.jini.core.lookup.ServiceRegistration;
import net.jini.core.entry.Entry;
import net.jini.core.lease.Lease;
import net.jini.core.lookup.ServiceTemplate;
import net.jini.core.lookup.ServiceMatches;
import javax.management.remote.*;
import javax.management.*;
import java.net.MalformedURLException;
import java.util.Map;
import java.util.List;
import java.util.ArrayList;
import java.util.Set;
import java.util.Iterator;
import java.io.IOException;
import java.io.Serializable;
import java.rmi.RMISecurityManager;
/**
* This class demonstrates how to use Jini as a lookup service for
* JSR 160 connectors. It shows how to lookup a JMXConnector from
* the Jini lookup service.
* <p>
* See README file and {@link #main(String[])} for more details.
* <p>
* Make sure to read the section "Binding with Lookup Services" of
* the JMX Remote API 1.0 Specification before looking at this example.
*/
public class Client {
private static boolean debug = false;
/**
* Get a pointer to the Jini Lookup Service.
* (See Jini documentation for more info).
* <p>
* The Jini Lookup Service URL is determined as follows:
* <p>
* If the System property <code>"jini.lookup.url"</code> is provided,
* its value is the Jini Lookup Service URL.
* <p>
* Otherwise, the default URL is assumed to be
* <code>"jini://localhost"</code>
*
* @return a pointer to the Jini Lookup Service.
*/
public static ServiceRegistrar getRegistrar()
throws IOException, ClassNotFoundException, MalformedURLException {
final String jurl =
System.getProperty("jini.lookup.url","jini://localhost");
final LookupLocator lookup = new LookupLocator(jurl);
final ServiceRegistrar registrar = lookup.getRegistrar();
if (registrar instanceof Administrable)
debug("Registry is administrable.");
return registrar;
}
/**
* Lookup JMXConnectors in the Jini Lookup Service.
*
* @param registrar A pointer to the Jini Lookup Service,
* returned by {@link #getRegistrar()}.
* @param name the AgentName of the JMXConnectors that should
* be returned. If <var>name</var> is null, then
* the JMXConnectors for all agents are returned
* (null is an equivalent for a wildcard).
* @return The list of matching JMXConnectors retrieved from
* the Jini Lookup Service.
*/
public static List lookup(ServiceRegistrar registrar,
String name) throws IOException {
final ArrayList list = new ArrayList();
// Returns only JMXConnectors. The filter could be made
// more strict by suplying e.g. RMIConnector.class
// (would only return RMIConnectors).
//
final Class[] classes = new Class[] {JMXConnector.class};
// Will return only those services for which the Name
// attribute was registered. Since JSR 160 specifies that
// the Name attribute is mandatory, this makes it possible
// to filter out all the services that do not conform
// to the spec.
// If <name> is null, then all services for which the
// Name attribute was specified will match, regardless of
// the value of that attribute. Otherwise, only those services
// for which Name matches the specified name will be returned.
//
final Entry[] serviceAttrs = new Entry[] {
// Add here the matching attributes.
new net.jini.lookup.entry.Name(name)
};
// Create a ServiceTemplate to do the matching.
//
ServiceTemplate template =
new ServiceTemplate(null,classes,serviceAttrs);
// Lookup all matching services in the Jini Lookup Service.
//
ServiceMatches matches =
registrar.lookup(template, Integer.MAX_VALUE);
// Retrieve the matching JMX Connectors.
//
for (int i = 0; i < matches.totalMatches; i++) {
debug("Found Service: " + matches.items[i].serviceID);
if (debug) {
// List the lookup attributes that where registered
// for that service.
if (matches.items[i].attributeSets != null) {
final Entry[] attrs = matches.items[i].attributeSets;
for (int j = 0; j < attrs.length ; j++) {
debug("\tAttribute["+j+"]=" + attrs[j]);
}
}
}
if (matches.items[i].service != null) {
// Service could be null if it can't be deserialized, because
// e.g. the class was not found.
// This will not happen with JSR 160 mandatory connectors
// however.
// Get the JMXConnector.
//
JMXConnector c = (JMXConnector)(matches.items[i].service);
debug("Found a JMXConnector: " + c);
// Add the connector to the result list.
list.add(c);
}
}
return list;
}
/**
* List all MBeans and their attributes.
*/
public static void listMBeans(MBeanServerConnection server)
throws IOException {
final Set names = server.queryNames(null,null);
for (final Iterator i=names.iterator(); i.hasNext(); ) {
ObjectName name = (ObjectName)i.next();
System.out.println("Got MBean: "+name);
try {
MBeanInfo info =
server.getMBeanInfo((ObjectName)name);
MBeanAttributeInfo[] attrs = info.getAttributes();
if (attrs == null) continue;
for (int j=0; j<attrs.length; j++) {
if (attrs[j].isReadable()) {
try {
Object o =
server.getAttribute(name,attrs[j].getName());
System.out.println("\t\t" + attrs[j].getName() +
" = "+o);
} catch (Exception x) {
System.err.println("JmxClient failed to get " +
attrs[j].getName());
x.printStackTrace(System.err);
}
}
}
} catch (Exception x) {
System.err.println("JmxClient failed to get MBeanInfo: " + x);
x.printStackTrace(System.err);
}
}
}
/**
* Trace a debug message.
*/
private static void debug(String msg) {
if (debug) System.out.println(msg);
}
/**
* Program Main
* <p>
* Lookup all JMX agents in the Jini Lookup Service and list
* their MBeans and attributes.
* <p>
* You may wish to use the following properties on the Java command line:
* <ul>
* <li><code>-Dagent.name=<AgentName></code>: specifies an
* AgentName to lookup (default is null, meaning any agent).</li>
* <li><code>-Djini.lookup.url=<jini-url></code>:
* the Jini Lookup Service URL (default is "jini://localhost"),
* see {@link #getRegistrar()}.</li>
* <li><code>-Ddebug="true|false"</code>: switch the Client debug flag
* on/off (default is "false").</li>
* </ul>
*/
public static void main(String[] args) {
try {
// Jini requires a security manager.
//
if (System.getSecurityManager() == null)
System.setSecurityManager(new RMISecurityManager());
// Get the value of the debug flag.
//
debug = (Boolean.valueOf(System.getProperty("debug","false"))).
booleanValue();
// Get AgentName to lookup. If not defined, all agents
// are looked up.
//
final String agentName = System.getProperty("agent.name");
// Get a pointer to the Jini Lookup Service.
//
final ServiceRegistrar registrar = getRegistrar();
debug("registrar is: " + registrar);
// Lookup all matching agents in the Jini Lookup Service.
//
List l = lookup(registrar,agentName);
// Attempt to connect to retrieved agents
//
System.out.println("Number of agents found : " + l.size());
int j = 1;
for (Iterator i=l.iterator();i.hasNext();j++) {
JMXConnector c1 = (JMXConnector) i.next();
if (c1 != null) {
// Connect
//
System.out.println(
"----------------------------------------------------");
System.out.println("\tConnecting to agent number "+j);
System.out.println(
"----------------------------------------------------");
debug("JMXConnector is: " + c1);
try {
c1.connect(null);
} catch (IOException x) {
System.err.println("Connection failed: " + x);
if (debug) x.printStackTrace(System.err);
continue;
}
// Get MBeanServerConnection
//
MBeanServerConnection conn =
c1.getMBeanServerConnection();
debug("Connection is:" + conn);
System.out.println("Server domain is: " +
conn.getDefaultDomain());
// List all MBeans
//
try {
listMBeans(conn);
} catch (IOException x) {
System.err.println("Failed to list MBeans: " + x);
if (debug) x.printStackTrace(System.err);
}
// Close connector
//
try {
c1.close();
} catch (IOException x) {
System.err.println("Failed to close connection: " + x);
if (debug) x.printStackTrace(System.err);
}
}
}
} catch (Exception x) {
System.err.println("Unexpected exception caught in main: " + x);
x.printStackTrace(System.err);
}
}
}
examples/Lookup/jini/java.policy
/*
* Copyright (c) 2004, Oracle and/or its affiliates. All rights reserved.
* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*/
/* A minimal security policy file for the browser. */
grant {
// needed by the GUI
// permission java.awt.AWTPermission "showWindowWithoutWarningBanner";
// permission java.awt.AWTPermission "accessEventQueue";
// needed by both the GUI and LookupDiscovery
permission java.lang.RuntimePermission "modifyThreadGroup";
permission java.lang.RuntimePermission "modifyThread";
// needed by LookupDiscovery
permission java.util.PropertyPermission "net.jini.discovery.*", "read";
permission java.util.PropertyPermission "jini.*", "read";
// multicast request address
// permission java.net.SocketPermission "224.0.1.85", "connect,accept";
// multicast announcement address
permission java.net.SocketPermission "224.0.1.84", "connect,accept";
// needed by both LookupDiscovery and the GUI
permission net.jini.discovery.DiscoveryPermission "*";
// unicast discovery, http: downloading, RMI
permission java.net.SocketPermission "*:1024-", "connect,accept";
// http: codebases
permission java.net.SocketPermission "*:80", "connect";
// ldap: codebases
permission java.net.SocketPermission "*:389", "connect";
// ldaps: codebases
permission java.net.SocketPermission "*:636", "connect";
// delete this one if you don't need to accept file: codebases
permission java.io.FilePermission "<<ALL FILES>>", "read";
// needed to allow the lookup proxy to perform debug duties
// (ex. display stack trace when unmarshal failures occur)
permission java.util.PropertyPermission "com.sun.jini.reggie.*", "read";
permission javax.management.MBeanServerPermission "*";
permission java.util.PropertyPermission "*", "read";
permission javax.management.MBeanPermission "*", "*";
permission javax.management.MBeanTrustPermission "*";
permission java.lang.RuntimePermission "*";
permission javax.security.auth.AuthPermission "doAsPrivileged";
};