Download Section 10 Advanced network Programming

Survey
yes no Was this document useful for you?
   Thank you for your participation!

* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project

Document related concepts
no text concepts found
Transcript
Programming Section 10
Lab Exercises September 2003
By James King
Contents
Contents ......................................................................................................................... 2
Table of Figures ............................................................................................................. 2
Section 10 Advanced network Programming ................................................................ 3
Handling Multiple Clients.......................................................................................... 3
Java Remote Method Invocation (RMI) .................................................................... 4
Setting up, Compiling and Running Java RMI clients. Servers and Registry ........... 7
Stubs....................................................................................................................... 7
Registry .................................................................................................................. 7
server ...................................................................................................................... 7
client ....................................................................................................................... 7
Table of Figures
Error! No table of figures entries found.
2
Section 10 Advanced network
Programming
Do not try this section until you have read and understand Java Serialization, Multiple
threads and the networking section.
Handling Multiple Clients
Both Java accept and receive block (i.e. stop the thread that calls them) until a
connection is made or there is data available to read. This means the thread that calls
accept or receive cannot do anything else until the wait is over. So if we program the
server with a single thread then only one client can connect to the server at a time.
Most of the time we want to be able to handle multiple clients and therefore the server
must be multi-threaded. There is potentially a similar problem for the client. If the
client calls receive because it is expecting a reply from the server it will sleep until the
reply arrives. This means that if the client has a GUI there is no thread available to
process the user clicking the mouse or typing so the GUI will seem to lock up! Worse
than this, if the client does not know when data will come from the server. For
instance, if the server is a chat server like IRC, then client requires multiple threads
one to wait for data from the server and another to send data to the server. It is
difficult in network programming to avoid writing multi-threaded programs.
Lets modify our hello world TCP server multi-threaded and leave the client as single
threaded for now. We will change the server so that as soon as it accepts a clients’
connection it will create a separate thread to handle that connection and loop around
again to accept the next client whilst the separate (slave) thread handles the
communication with the new client.
ServerSocket sv=new ServerSocket(6666,2);
while(true)
{
Socket s=sv.accept();
Thread sl=new Thread(new slave(s));
sl.start();
}
The slave thread needs to communicate with the newly connected client so the socket
used to communicate with the client is passed to the slave Thread when it is
instantiated.
3
public class slave implements Runnable
{
Socket sock=null;
public slave(Socket s)
{
sock=s;
}
public void run()
{
InputStream i=sock.getInputStream();
DataInputStream oi=new DataInputStream(i);
String h=oi.readUTF();
Thread.sleep(3000);
System.out.println(h);
}
}
To prove the server can accept multiple clients we can add delays in the client so you
can run more than one at the same time.
Thread.sleep(1000);
Sleep makes the thread sleep for 1000 mill-seconds or 1 second. You of course can
use a larger number! However, sleep can be interrupted if it is it will cause an
Exception therefore you will need a try catch around it!
Java Remote Method Invocation (RMI)
Up to now, you have called many methods inside you own program such as
Monster m=new Monster();
m.take_damage(25);
But the only way to communicate with another program (possibly running on anther
machine) is to use TCP or UDP network programming. This is not very natural. Why
can’t you just call a method in an instance of a class running on another machine or
inside a different program and expect Java to figure out how to do it. Java RMI allows
you to do just that! With only a little additional code and effort you can call methods
in other Java programs running on other machines just as if the method was inside one
of you classes inside you program. This is a nice feature of Java.
4
You need to tell Java which methods can be called from the outside world. (For
security reasons you might not allow every method in every class to be called from
anywhere on the Internet!!!!!!). To do this you create an interface listing each method
that you want to be called remotely.
import java.rmi.*;
public interface remoteserver extends Remote
{
public void helloworld() throws java.rmi.RemoteException;
}
All of the Java rmi code is in a package called rmi so you need to import it. The
interface must extend Remote and each exported method must be declared as possibly
throwing java.rmi.RemoteException.
Naturally the interface contains no code so you must write a class that implements this
interface and provides code for each method header in the interface. Sounds too
simple? Well yes, there are a few more details you need to know to get you remote
class available to the rest of the world. Firstly you need to specify the communication
system between the callers and you remote object. This is usually
java.rmi.server.UnicastRemoteObject
UnicastRemoteObject is a Java class in the rmi package and your remotely callable
class must extend it as well as implementing the Remote interface. You also need to
register you class with the Java remote object invocation registry. This registry stores
a list of all the remotely accessible objects and methods and acts as a central directory.
You do this by creating an instance of you remotely assessable class and passing it as
a parameter to a static method (rebind) in a static class (Naming). You also need to
specify which machine the class is running on. The format for this is rather like a
URL for a web page. First is the protocol in this case rmi next is the location of the
remote class in this case localhost (this machine) and finally is the name of the class
in this case server.
server s=new server();
Naming.rebind("rmi://localhost/server",s);
5
Bellow is the entire code for the server.
import java.rmi.*;
import java.rmi.server.*;
public class server extends java.rmi.server.UnicastRemoteObject implements
remoteserver
{
public void helloworld() throws java.rmi.RemoteException
{
System.out.println("hello world");
}
public static void main(String args[])
{
server s=new server();
Naming.rebind("rmi://localhost/server",s);
}
}
For the client to call a method in the server the client must use the registry to find the
server. Calling the lookup method in the Naming class does this. The lookup method
needs to know the name of the class to find so you pass the same URL like string as
the remote class was registered with
Naming.lookup("rmi://localhost/server");
The entire client code is
import java.rmi.*;
public class client
{
public static void main(String args[])
{
remoteserver s=(remoteserver) Naming.lookup("rmi://localhost/server");
s.helloworld();
}
}
Naming.lookup returns a stub that can be used to communicate with the remote
server. This stub must be typecast into the name of the interface the remote server
implements. In this case remoteserver. You can then use the stub to call the remote
method helloworld!
6
Setting up, Compiling and Running Java RMI clients.
Servers and Registry
BlueJ does not fully support Java RMI yet so there are some things you need to do
using MS-DOS and the SUN Java Software Development kit (JDK).
Stubs
The stubs and skeleton are not generated by BlueJ and require a compiler called rmic
this is part of the SUN J2sdk you installed along with BlueJ. Load up and command
prompt or Msdos window. type in dir, if you are not in the directory that contains your
RMI code cd (change directory) to it. Run the rmic compiler on the server by typing
in
c:\j2sdk1.4.2_01\bin\rmic server
(You may need to replace c:\j2sdk1.4.2_01 with the location and version of the Java
you have installed.)
This should compile the server class and generate the stub and skeleton
Registry
Before running the server you need to run the registry so using the same MS-DOS
window type in
c:\j2sdk1.4.2_01\bin\rmiregistry
(Again you may need to replace c:\j2sdk1.4.2_01 with the location and version of the
Java you have installed. Leave the registry running the entire time you experiment
with rmi)
Note the registry should be run in the same directory as the RMI class files you
have just created.
server
Run the server from BlueJ as normal and if it crashes with in Exception during the
binding then either you have not run the registry or the registry was run in a different
directory from the one the server class file is in.
client
Run the client last in another copy of BlueJ. If the client generates an Exception
during the lookup you probably have not run the registry and registered the server.
Once the client has run the server should say “hello world”.
7