Currently
we send a message to the server with a user for whom that message is intended.
We send these both as Strings. But proper object oriented design
would tell us to send one object instead of a series of Strings and primitives.
So let's make an object, called Message, that has our two String attributes
plus one more: String sender. This object will implement serializable.
Then, when we call sendMessage on the server, we'll pass it this Message
object.
/*
* Message.java
*
* Created on May 8, 2003, 11:20 AM
*/
package chat;
/**
*
* @author default
* @version
*/
public class Message implements java.io.Serializable {
// Create our attributes.
String message = new String();
String destination = new String();
String user = new String();
/** Creates new Message */
public Message() {
}
/** Creates a message with properties. */
public Message(String message, String destination,
String user) {
this.message = message;
this.destination = destination;
this.user = user;
System.out.println("Message
Created.");
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public String getDestination (){
return destination;
}
public void setDestination (String destination)
{
this.destination = destination;
}
public String getUser() {
return user;
}
public void setUser(String user) {
this.user = user;
}
}
/*
* Chat.java
*
* Created on April 28, 2003, 11:55 PM
*/
package chat;
import java.rmi.*;
/** Remote interface.
*
* @author default
* @version 1.0
*/
public interface Chat extends java.rmi.Remote {
public void login (String user, String password)
throws RemoteException;
public void sendMessage (String message, String
user) throws RemoteException;
public void sendMessage (Message message) throws
RemoteException;
}
-
Convenience method on ChatImpl:
package chat;
/*
* ChatImpl.java
*
* Created on April 28, 2003, 11:48 PM
*/
import java.rmi.*;
import java.rmi.server.*;
import java.rmi.registry.*;
import java.net.MalformedURLException;
/** Unicast remote object implementing Chat interface.
*
* @author default
* @version 1.0
*/
public class ChatImpl extends java.rmi.server.UnicastRemoteObject
implements Chat {
BulletinBoard board;
/** Constructs ChatImpl object and exports it
on default port.
*/
public ChatImpl() throws RemoteException {
super();
// Fire up our JFrame
here.
board = new BulletinBoard();
board.show();
}
/** Constructs ChatImpl object and exports it
on specified port.
* @param port The port for exporting
*/
public ChatImpl(int port) throws RemoteException
{
super(port);
}
/** Register ChatImpl object with the RMI registry.
* @param name - name identifying the service
in the RMI registry
* @param create - create local registry
if necessary
* @throw RemoteException if cannot be
exported or bound to RMI registry
* @throw MalformedURLException if name
cannot be used to construct a valid URL
* @throw IllegalArgumentException if null
passed as name
*/
public static void registerToRegistry(String
name, Remote obj, boolean create) throws RemoteException, MalformedURLException{
if (name == null) throw
new IllegalArgumentException("registration name can not be null");
try {
Naming.rebind(name, obj);
} catch (RemoteException
ex){
if (create) {
Registry r = LocateRegistry.createRegistry(Registry.REGISTRY_PORT);
r.rebind(name, obj);
} else throw ex;
}
}
/** Main method.
*/
public static void main(String[] args) {
System.setSecurityManager(new
RMISecurityManager());
try {
ChatImpl obj = new ChatImpl();
registerToRegistry("ChatImpl", obj, true);
} catch (RemoteException
ex) {
ex.printStackTrace();
} catch (MalformedURLException
ex) {
ex.printStackTrace();
}
}
public void login(String user, String password)
{
}
public void sendMessage(String message, String
user) {
System.out.println("Message:
" + message + " User: " + user);
// call method on JFrame
to add this to our list.
board.addMessage(message);
}
/** For sake of time,
just make a convenience method to the existing sendMessage method. */
public void sendMessage(Message
message) {
sendMessage(message.getMessage(), message.getUser());
}
}
-
Slight change in ChatForm:
/*
* ChatForm.java
*
* Created on May 1, 2003, 1:18 AM
*/
package chat;
import java.rmi.*;
import java.rmi.registry.*;
/**
*
* @author default
*/
public class ChatForm extends javax.swing.JFrame {
// Globally visible reference to the stub via
interface.
Chat chat;
/** Creates new form ChatForm */
public ChatForm() {
// Get the stub.
// Change the URL if
connecting to a different machine.
try {
chat = (Chat)Naming.lookup("rmi://localhost/ChatImpl");
} catch (Exception e)
{
System.out.println("Exception while attempting to lookup ChatImpl.
Message: " + e.getMessage());
e.printStackTrace();
}
initComponents();
}
/** This method is called from within the constructor
to
* initialize the form.
* WARNING: Do NOT modify this code. The
content of this method is
* always regenerated by the Form Editor.
*/
private void initComponents() {
jLabel1 = new javax.swing.JLabel();
jPanel1 = new javax.swing.JPanel();
btnSend = new javax.swing.JButton();
jScrollPane1 = new javax.swing.JScrollPane();
txtMessage = new javax.swing.JTextArea();
addWindowListener(new
java.awt.event.WindowAdapter() {
public void windowClosing(java.awt.event.WindowEvent evt) {
exitForm(evt);
}
});
jLabel1.setText("Send
a Message to the Bulletin Board");
getContentPane().add(jLabel1,
java.awt.BorderLayout.NORTH);
btnSend.setText("Send");
btnSend.addActionListener(new
java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
btnSendActionPerformed(evt);
}
});
jPanel1.add(btnSend);
getContentPane().add(jPanel1,
java.awt.BorderLayout.SOUTH);
txtMessage.setRows(4);
jScrollPane1.setViewportView(txtMessage);
getContentPane().add(jScrollPane1,
java.awt.BorderLayout.CENTER);
pack();
}
private void btnSendActionPerformed(java.awt.event.ActionEvent
evt) {
// Send a message to
the bulletin board.
try {
// Make a message. Hardcode some thing in until we prompt the user
for this information.
Message message = new Message(txtMessage.getText(), "BulletinBoard", "RMI
User");
// chat.sendMessage(txtMessage.getText(), "BulletinBoard");
chat.sendMessage(message);
} catch (Exception e)
{
System.out.println("RemoteException while attempting to send message to
Bulletin Board. Message: " + e.getMessage());
}
}
/** Exit the Application */
private void exitForm(java.awt.event.WindowEvent
evt) {
System.exit(0);
}
/**
* @param args the command line arguments
*/
public static void main(String args[]) {
// Set the security
policy and security manager.
System.setProperty("java.security.policy",
"client.policy");
System.setSecurityManager(new
RMISecurityManager());
new ChatForm().show();
}
// Variables declaration - do not modify
private javax.swing.JLabel jLabel1;
private javax.swing.JPanel jPanel1;
private javax.swing.JButton btnSend;
private javax.swing.JScrollPane jScrollPane1;
private javax.swing.JTextArea txtMessage;
// End of variables declaration
}
-
I had some trouble deploying this initially. I was getting AbstractMethodError,
which indicates one class is out of synch with the others. In other
words, perhaps one class was not copied once it was updated. I verified
a number of items, deleted and recopied all of my classes, and it finally
worked.
-
The view does not change, except for informational messsages printed to
standard output, so I'll spare the screen captures.
Passing Remote Objects
|