RMI einfacher Chat - Callbacks(?) funktionieren nicht

feuerball

Mitglied
Hallo zusammen,

ich muss für eine Übung einen Chat mit RMI programmieren. Wir haben 2 Interfaces gegeben:

ChatService:
Java:
package com.jchat.interfaces;

import java.rmi.Remote;
import java.rmi.RemoteException;
import java.util.List;

public interface ChatService extends Remote {

	void register(ClientService cs) throws RemoteException;
	void unregister(ClientService cs) throws RemoteException;
	void message(String name, String msgs) throws RemoteException;
	List<String> getUserList() throws RemoteException;
	
}

und ClientService:
Java:
package com.jchat.interfaces;

public interface ClientService {

	void message(String name, String msg);
	String getName();
	void updateClients();
	
}

Dazu sollen wir eine Klasse ChatServer schreiben. Meine sieht bisher so aus:
Java:
package com.jchat.server;

import java.net.MalformedURLException;
import java.rmi.Naming;
import java.rmi.RemoteException;
import java.rmi.registry.LocateRegistry;
import java.rmi.registry.Registry;
import java.rmi.server.UnicastRemoteObject;
import java.util.ArrayList;
import java.util.List;

import com.jchat.interfaces.ChatService;
import com.jchat.interfaces.ClientService;

public class ChatServer extends UnicastRemoteObject implements ChatService {
	
	private List<ClientService> clients;

	protected ChatServer() throws RemoteException {
		super();
		this.clients = new ArrayList<ClientService>();
	}

	/**
	 * 
	 */
	private static final long serialVersionUID = 918273645L;

	@Override
	public void register(ClientService cs) throws RemoteException {
		this.clients.add(cs);
		System.out.println("Client " + cs.getName() + " has connected");
		for (ClientService client : clients) {
			client.updateClients();
		}
	}

	@Override
	public void unregister(ClientService cs) throws RemoteException {
		this.clients.remove(cs);
		System.out.println("Client " + cs.getName() + " has disconnected");
		for (ClientService client : clients) {
			client.updateClients();
		}
	}

	@Override
	public void message(String name, String msg) throws RemoteException {
		System.out.println(name + ": " + msg);
		for (ClientService client : this.clients) {
			client.message(name, msg);
		}
	}

	@Override
	public List<String> getUserList() throws RemoteException {
		List<String> clientNames = new ArrayList<String>();
		for (ClientService client : this.clients) {
			clientNames.add(client.getName());
		}
		return clientNames;
	}
	
	public static void main(String[] args) {
		try {
			//rmiregistry starten
			LocateRegistry.createRegistry(Registry.REGISTRY_PORT);
			System.out.println(LocateRegistry.getRegistry());
			Naming.rebind("chat", new ChatServer());
			System.out.println("Server started");
		} catch (RemoteException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (MalformedURLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}

}

Zum Schluss sollen wir die Klasse ChatClient schreiben. Bei mir enthält Sie außerdem eine GUI:
Java:
package com.jchat.client;

import java.awt.BorderLayout;
import java.awt.event.ActionEvent;
import java.io.Serializable;
import java.net.MalformedURLException;
import java.rmi.Naming;
import java.rmi.NotBoundException;
import java.rmi.RemoteException;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;

import javax.swing.AbstractAction;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;
import javax.swing.KeyStroke;
import javax.swing.ScrollPaneConstants;

import com.jchat.interfaces.ChatService;
import com.jchat.interfaces.ClientService;

public class ChatClient extends JFrame implements ClientService, Serializable {

	/**
	 * 
	 */
	private static final long serialVersionUID = 6574839201L;
	private String name;
	private ChatService remote;
	//GUI Elemente
	private JScrollPane jScrollPane1;
	private JScrollPane jScrollPane2;
	private JTextArea chat;
	private JTextArea users;
	private JPanel textPanes;
	private JTextField cmdLine;
	private DateFormat df;
	private boolean fl;
	private boolean connected;
	//

	public ChatClient() {
		super("jChat");
		this.df = new SimpleDateFormat("HH:mm");
		this.fl = true;
		this.connected = false;
		this.name = "";
		initGUI();
		new Thread(new Runnable() {

			@Override
			public void run() {
				// TODO Auto-generated method stub
				
			}
			
		}).start();
	}

	@Override
	public void message(String name, String msg) {
		System.out.println("client message");
		this.chat.append(printLine(name, msg));
	}

	@Override
	public String getName() {
		return this.name;
	}

	private void connect(String ip) {
		try {
			this.remote = (ChatService) Naming.lookup("//" + ip + "/chat");
			this.remote.register(this);
		} catch (MalformedURLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (RemoteException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (NotBoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} finally {
			this.connected = true;
		}
	}

	private void disconnect() {
		try {
			this.remote.unregister(this);
			this.connected = false;
		} catch (RemoteException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	private void initGUI() {

		// Frame Layout setzen
		this.setLayout(new BorderLayout());

		// Komponenten initilisieren
		this.chat = new JTextArea(
				printLine("jChat", "Welcome to jChat")
						+ printLine("jChat",
								"Following commands are available:")
						+ printLine("jChat",
								"$nickname <YourPrefferedName> (No spaces!)")
						+ printLine("jChat",
								"$connect <IP> (Server must run jChat)")
						+ printLine("jChat", "$disconnect")
						+ printLine("jChat",
								"You can connect to a Server if you have set a nickname")
						+ printLine("jChat",
								"Press <Ctrl+Enter> to submit your input")
						+ printLine("jChat", "Let's start with your nickname"),
				20, 40);
		this.users = new JTextArea("Users", 20, 15);
		this.jScrollPane1 = new JScrollPane(this.chat);
		this.jScrollPane2 = new JScrollPane(this.users);
		this.cmdLine = new JTextField(50);
		this.textPanes = new JPanel(new BorderLayout());

		this.chat.setEditable(false);
		this.chat.setLineWrap(true);
		this.chat.setWrapStyleWord(true);
		this.users.setEditable(false);
		this.jScrollPane1
				.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);
		this.jScrollPane2
				.setHorizontalScrollBarPolicy(ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);

		this.cmdLine.getInputMap().put(KeyStroke.getKeyStroke("control ENTER"),
				"send");
		this.cmdLine.getActionMap().put("send", new AbstractAction("send") {
			/**
			 * 
			 */
			private static final long serialVersionUID = 1L;

			public void actionPerformed(ActionEvent evt) {
				parseInput();
			}
		});

		// Komponenten zusammensetzen
		this.textPanes.add(this.jScrollPane1, BorderLayout.LINE_START);
		this.textPanes.add(this.jScrollPane2, BorderLayout.LINE_END);

		this.add(this.textPanes, BorderLayout.PAGE_START);
		this.add(this.cmdLine, BorderLayout.PAGE_END);

		// Frame anzeigen
		this.setDefaultCloseOperation(EXIT_ON_CLOSE);
		this.setResizable(false);
		this.pack();
		this.setVisible(true);

	}

	private void parseInput() {

		String input = this.cmdLine.getText();

		if (!input.isEmpty()) {
			if (input.startsWith("$nickname")) {
				String[] splittedInput = input.split(" ");
				if (splittedInput.length == 2 && this.name.isEmpty()) {
					this.name = splittedInput[1];
					this.chat.append(printLine("jChat", "So you are "
							+ this.name));
				}
				if (splittedInput.length == 1) {
					this.chat.append(printLine("jChat",
							"You have to submit your name"));
				}
				if (splittedInput.length > 2) {
					this.chat.append(printLine("jChat",
							"You can only have one name"));
				}
			} else if (input.startsWith("$connect")) {
				String[] splittedInput = input.split(" ");
				if (splittedInput.length == 2 && !this.name.isEmpty() && !this.connected) {
					connect(splittedInput[1]);
					this.chat.append(printLine("jChat", "Ready to go"));
				}
				if (splittedInput.length == 1) {
					this.chat.append(printLine("jChat",
							"You have to submit an IP address"));
				}
				if (splittedInput.length > 2) {
					this.chat.append(printLine("jChat",
							"This is not an IP address"));
				}
			} else if (input.startsWith("$disconnect") && this.connected) {
				disconnect();
			} else if (this.connected) {
				try {
					this.remote.message(this.name, input);
				} catch (RemoteException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			} else {
				this.chat.append(printLine("jChat",
						"I don't know what to do. Specify your request"));
			}
		}

		this.cmdLine.setText("");

	}

	private String printLine(String name, String message) {
		if (this.fl) {
			this.fl = false;
			return name + " (" + df.format(new Date()) + "):\t" + message;
		} else {
			return "\n" + name + " (" + df.format(new Date()) + "):\t"
					+ message;
		}
	}


	public static void main(String[] args) {
		new ChatClient();
	}

	@Override
	public void updateClients() {
		try {
			List<String> clients = this.remote.getUserList();
			this.users.setText("Users:");
			for (String client : clients) {
				this.users.append("\n" + client);
			}
			System.out.println("Clients have been updated");
		} catch (RemoteException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}

}

Das Programm läuft folgendermaßen ab (Eingaben werden mit Strg+Enter abgesendet):
  1. Man muss mit $nickname <nickname> einen Name festlegen
  2. Man muss sich mit $connect <IP> zum Server verbinden
  3. Danach soll man Nachrichten verschicken können
  4. Mit $disconnect kann man die Verbindung trennen

Das Problem ist, dass ich keine Nachrichten verschicken kann. An- und abmelden funktioniert, aber wenn ich eine Nachricht verschicke, versucht der Server diese auszugeben. Zum verschicken rufe ich auf dem Server die Methode
Code:
message()
auf. Diese geht die Liste der angemeldeten Clients durch und ruft bei jedem Client die gleichnamige Methode
Code:
message()
auf. Die
Code:
message()
Methode vom Client soll die übermittelte Nachricht in einer JTextArea ausgeben. Allerdings erscheinen auf der Konsole vom Server die Meldungen, dass eine Nachricht eingegangen ist (Ich habe einfach ein paar Meldungen über sysout zur Kontrolle eingebaut).

Ich hoffe ihr könnt mir sagen wo der Denkfehler ist oder ob ich da komplett falsch rangehe, ich stehe da ganz schön auf dem Schlauch...

Ich habe außerdem den src ordner aus meinem eclipse Projekt bei mediafire hochgeladen, falls ihr damit einen besseren Einblick bekommt.

Danke schon einmal im Voraus!
 

feuerball

Mitglied
Ich hab's jetzt selber hinbekommen. Der Client muss einfach nur von
Code:
UnicastRemoteObject
erben und alles läuft.
 

feuerball

Mitglied
Ja, aber das hat nicht geklappt. Zwischen einem mac und einem Windows Rechner hat's auch nicht geklappt. Zwischen 2 Windows Rechnern im LAN hat's funktioniert, über hamachi hat's allerdings nicht funktioniert. Ich habe auch ein Portforwarding in meinem Router eingestellt, was aber auch nichts bewirkt hat.

Weißt du warum das nicht klappt oder warum fragst du?
 

zion150

Neues Mitglied
Ich hab's jetzt selber hinbekommen. Der Client muss einfach nur von
Code:
UnicastRemoteObject
erben und alles läuft.

Wie funktioniert denn Mehrfachvererbung in Java? Ich mache doch schon ein extends JFrame beim Client.
Wobei es mich allgemein auch interessieren würde, wie man hier die Gui von dem Programm trennen kann, also ohne extends JFrame.
 
M

Marcinek

Gast
1. Warum Hijackst du einen uralten Threat?
2. Schau dir mal MVC an. (Man muss fast nie JFrame extenden)

Gruß,

Martin
 
T

tröööt

Gast
grundsätzlich : mehrfachvererbung und polymorphie gibt es in java NICHT !

ich weis zwar nicht was TO damals gemacht hat ... da das thema ja nun doch schon ein gewisses alter hat ... aber "extends JFrame" oder "implements ActionListener" sind typische anfänger fehler ...

man sollte grundsätzlich (außnahme : applet) alle logischen einheiten von ein andere trennen und auch in eigene klassen schreiben ...

das ganze hat was mit design-pattern zu tun ... deine antwort auf deine frage liegt also im pattern ... und danach darfst du bitte selbst googlen
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
S Einfacher Multiuser chat in java Netzwerkprogrammierung 18
H Einfacher Server funktioniert nicht Netzwerkprogrammierung 1
A Socket Wie ein einfacher Multithreads Service mit Telnet als Client mit Observable/Observer gelöst.... Netzwerkprogrammierung 0
B Einfacher Server mit Jetty Netzwerkprogrammierung 3
D Apache CXF, JAX-WS Problem bei Arrays - einfacher Server Netzwerkprogrammierung 2
S Socket Einfacher filetransfer Netzwerkprogrammierung 10
B Einfacher Proxy Server Netzwerkprogrammierung 29
M Socket Probleme mit einfacher Socketverbindung Netzwerkprogrammierung 3
L einfacher server ohne threads Netzwerkprogrammierung 4
P Einfacher Server/Client Netzwerkprogrammierung 5
L Einfacher Proxy-Server Netzwerkprogrammierung 6
A einfacher Transfer mit Applets Netzwerkprogrammierung 4
C Einfacher Filedownload mit Sockets geht nicht für pdffiles Netzwerkprogrammierung 16
T Einfacher Servlet-Server Netzwerkprogrammierung 8
H Socket Chat entwickeln mit Java Server Client Netzwerkprogrammierung 4
L Chat Fenster Netzwerkprogrammierung 1
J Socket Ein Chat Server Tutorial Netzwerkprogrammierung 8
S Java Chat Server Netzwerkprogrammierung 8
J Chat Server starten über GUI problem Netzwerkprogrammierung 4
P Chat in Java Netzwerkprogrammierung 3
C Java Chat Admin Kenzeichnung Netzwerkprogrammierung 14
D Chat Server/mehre Client Netzwerkprogrammierung 9
Androbin Socket Fehlerhafter Applet-Chat Netzwerkprogrammierung 12
C Microsoft Comic Chat Netzwerkprogrammierung 0
G Socket Socket verbindung für Chat System Netzwerkprogrammierung 3
O Chat (Server) sendet an verschieden Benutzer. Netzwerkprogrammierung 10
J Chat programmieren Netzwerkprogrammierung 12
L Chat Server programmieren Netzwerkprogrammierung 10
TheJavaKid Webcam-Chat im Applet (ChatRoulette Klon) Netzwerkprogrammierung 10
H Socket Java Chat - Verbindung zum Server fehlgeschlagen. Netzwerkprogrammierung 5
K Socket Chat-GUI eigenes Event nach Empfangen Netzwerkprogrammierung 2
K chat Netzwerkprogrammierung 13
L Socket Chat funktioniert nicht Netzwerkprogrammierung 2
T Socket Java Chat Netzwerkprogrammierung 2
xDarkSunx Chat JFrame Netzwerkprogrammierung 3
xDarkSunx Hilfe Chat Login Netzwerkprogrammierung 7
E JAVA Chat Netzwerkprogrammierung 19
C Java Chat funktioniert nicht richtig Netzwerkprogrammierung 6
I Chat-Client empfängt nichts vom Server Netzwerkprogrammierung 3
A Socket UDP Chat Verbindungsproblem im WWW (Server sendet ins leere) Netzwerkprogrammierung 11
A Multi-User-Chat Netzwerkprogrammierung 2
M Socket Chat-Client-Problem Netzwerkprogrammierung 8
E Userliste für Chat Applet Netzwerkprogrammierung 4
L Socket Chat Server für mehrere Clients Netzwerkprogrammierung 7
J Framework/ Muster für Chat-ähnliches Programm gesucht Netzwerkprogrammierung 2
AMStyles Client Server basierter Chat Netzwerkprogrammierung 7
M chat als applet umgeschrieben - unbekannter fehler :( Netzwerkprogrammierung 2
P Socket Chat selbst bauen + Multiusereditor Netzwerkprogrammierung 13
T Java Chat über UDP Netzwerkprogrammierung 7
Developer_X Habe fragen zur Chat Programmierung Netzwerkprogrammierung 4
P Java Multiuser Chat hohe Systemauslastung Netzwerkprogrammierung 24
D Hilfe ich komme bei meinem UDP chat Server nicht mehr weiter Netzwerkprogrammierung 9
B Die alte Leier: "Chat" Netzwerkprogrammierung 3
M chat funktioniert nicht (Connection refused: connect) Netzwerkprogrammierung 3
R Java-Chat-Applet funktioniert nur in Eclipse Netzwerkprogrammierung 3
S Client-Server Chat Problem nur im lokalen Netztwerk Netzwerkprogrammierung 23
DamienX Chat Socketserver/Client. wo ist das Problem? Netzwerkprogrammierung 2
J Client-Client-Chat ohne Serverbeteiligung Netzwerkprogrammierung 2
A Wichtig für einen Chat? Netzwerkprogrammierung 4
S Java Applet Chat Grundsatzfrage Netzwerkprogrammierung 6
R Java Chat über Inet connecten Netzwerkprogrammierung 3
F Chat Programm. Verständnisfrage while-Schleife Netzwerkprogrammierung 7
P Probleme bei Chat programm Netzwerkprogrammierung 2
C Voice Chat Netzwerkprogrammierung 3
G FAQ Chat geht nicht ? Netzwerkprogrammierung 4
T Schriftfarbe im Chat ändern Netzwerkprogrammierung 2
G ActionEvent klappt beim Chat nicht Netzwerkprogrammierung 5
J Kleines Problem mit Chat Server Netzwerkprogrammierung 2
T Chat-Client Netzwerkprogrammierung 12
G Chat zwischen applets: möglich? Netzwerkprogrammierung 2
T Chat mit mehreren Clients Netzwerkprogrammierung 3
C Chat , Streamproblem, PumpingException, Danke Netzwerkprogrammierung 2
S RMI Chat Problem, Client bekannt machen Netzwerkprogrammierung 2
V probleme mit dem chat programm Netzwerkprogrammierung 4
K Lokaler Chat Netzwerkprogrammierung 5
S Chat aufs Internet ausweiten Netzwerkprogrammierung 5
J Router behindert Chat Netzwerkprogrammierung 9
S Knuddels Chat System: Bot / Nachrichten verschicken? Netzwerkprogrammierung 6
G Chat - was brauch ich Netzwerkprogrammierung 2
André B. Brauche Hilfe bei Chat Netzwerkprogrammierung 6
K Problem mit "Chat" Netzwerkprogrammierung 2
N Java-Chat (lauffähig) macht Probleme auf der Konsole Netzwerkprogrammierung 6
Paule Acces denied bei Chat Netzwerkprogrammierung 6
B Multi-chat Problem Netzwerkprogrammierung 3
N Java Chat-Problem Netzwerkprogrammierung 4
G Java Chat mit HTML Cleint Netzwerkprogrammierung 3
G Chat Programm - was ist los? Netzwerkprogrammierung 9
A server mit 2 Ports : Mit und ohne SSL Chat system Netzwerkprogrammierung 10
Z chat: wann http und wann sockets verwenden? Netzwerkprogrammierung 11
M Socket Verbindungen für einen Chat Netzwerkprogrammierung 10
R Mini-Chat löst BindException aus Netzwerkprogrammierung 7
F Multiclient Chat Netzwerkprogrammierung 12
K Chat: Nur 1 Verbindung zum Server möglich :( Netzwerkprogrammierung 6
K Chat: Verbindung kommt nicht zu stande Netzwerkprogrammierung 6
S JAV07P SGD client/server chat Netzwerkprogrammierung 4
C IRC CHAT auslesen -> Sockets/input und output Streams Netzwerkprogrammierung 9

Ähnliche Java Themen

Neue Themen


Oben