RMI: Programmer's Checklist
Source
The interface
-
Create or modify public interface XYZ extends java.rmi.Remote
-
Add the Remote method.
public <return-type> methodName( <parameter-list> throws java.rmi.RemoteException;
-
The return type and all the parameters need to either:
-
implement java.io.Serializable or be a subclass of a class that does, or
-
be a Remote object (i.e., implement an interface that extends Remote directly
or indirectly).
The server (implementation of the interface)
-
implements XYZ.
-
has a no-argument constructor that throws RemoteException.
-
The main method that instantiates a server object:
-
sets a security manager ( needed, only if the server loads classes
not found in its CLASSPATH) :
if ( System.getSecurityManager() == null
)
{
System.setSecurityManager(
new java.rmi.RMISecurityManager() );
}
-
constructs the remote object (can throw a RemoteException: declare this
in the throws clause or place within a try-catch).
-
may need to bind the object to a service reference String in its machine's
rmiregistry with the bind or rebind methods.
-
If an external rmiregistry is running on the machine:
java.rmi.Naming.rebind("HelloServer", obj);//
obj refers to the constructed remote object server; "HelloServer" illustrates
the service reference String.
-
The server can start an rmiregistry internally (i.e., within its
own JVM) on some port. Then, we don't have rmiregistries running in the
background on machines where people forgot to terminate the rmiregistries
before they logged out. See janet.services.Hsp.java for an example of this
(in its main method).
The client
-
sets a SecurityManager (see server instructions).
-
gets a reference to the remote object
Hello hello = (Hello) Naming.lookup("//" + machineName + "/HelloServer");
// machineName is a String containing either the domain name or the IP
address of the machine on whch the server and rmiregistry are running.
This can throw various exceptions (see Java API for java.rmi.Naming.lookup).
So, it must be within a try-catch or the method must include these exceptions
in its throws clause.
-
invokes a remote method on the reference:
-
The invocation must either
-
be within a try-catch block for RemoteException
-
include the RemoteException in the invoking method's throws clause
Compiling
-
compile all the .java files as usual.
-
rmic all remote objects.
Running
For example, the command below (which should be all on 1 line) runs a Java
application called Application. The system expects the policy file called
policy
to be in the directory from which the java command executes.
java -Djava.rmi.server.codebase=http://www.cs.ucsb.edu/~cappello/classes/
\
-Djava.security.policy=policy
\
Application <command-line parameters
go here>
I need class files in my public_html/classes directory to be readable by
all. The classes directory needs to be readable and executable by all.
The trailing slash on the codebase specification
is crucial.
Runtime Exceptions
-
java.io.NotSerializableException
-
The object in question does not implement java.io.Serializable
-
java.security.AccessControlException: access denied
-
The JVM may not have access to a policy file, either because it is missing
or unreadable, or the specification of where it is (on the command line)
is incorrect.