Socket Server/Client Kommunikation

Tiding

Aktives Mitglied
Hallo,

ich habe folgende 3 Klassen erstellt:

Server:
Java:
public class Server {
    int clients = 0;
   
    public static void main(String[] args){
        Server server = new Server();
        try {
            server.test();
        }catch (IOException e){
            e.printStackTrace();
        }
    }
    void test() throws IOException {
        int port = 11111;
        ServerSocket serverSocket = new ServerSocket(port);
        System.out.println("Warte auf Anmeldung...");
        Socket client1 = warteAufAnmeldung(serverSocket);
        ErwarteNachricht ew1 = new ErwarteNachricht(client1);
        Thread nachrichtVerwalter1 = new Thread(ew1);
        nachrichtVerwalter1.start();
        System.out.println("Warte auf 2. Client...");
        Socket client2 = warteAufAnmeldung(serverSocket);
        ErwarteNachricht ew2 = new ErwarteNachricht(client2);
        Thread nachrichtVerwalter2 = new Thread(ew2);
        nachrichtVerwalter2.start();
        System.out.println("2 Clients sind erfolgreich angemeldet");
        while(true){
            //System.out.println("in while");
            if(ew1.hatNachricht()){
                String nachrichtClient1 = ew1.getNachricht();
                System.out.println("Client1: " + nachrichtClient1);
                schreibeNachricht(client2, "Client1: ", nachrichtClient1);
                ew1.resetNachricht();
            }
            if(ew2.hatNachricht()){
                String nachrichtClient2 = ew2.getNachricht();
                System.out.println("Client2: " + nachrichtClient2);
                schreibeNachricht(client1, "Client2: ",nachrichtClient2);
                ew2.resetNachricht();
            }
            //System.out.println("end while");
        }
    }
    Socket warteAufAnmeldung(ServerSocket serverSocket) throws IOException {
        Socket socket = serverSocket.accept();
        System.out.println("Client angemeldet!");
        clients++;
        return socket;
    }
    void schreibeNachricht(Socket socket,String vonClient, String nachricht) throws IOException {
         PrintWriter printWriter =
             new PrintWriter(
                 new OutputStreamWriter(
                  socket.getOutputStream()));
         printWriter.print(vonClient+nachricht);
         System.out.println(nachricht);
         printWriter.flush();
    }
}

Client:
Java:
public class Client {
    public static void main(String[] args){
        Client client = new Client();
        try{
            client.test();
        } catch (IOException e){
            e.printStackTrace();
        }
    }
    void test() throws IOException {
        String ip = "127.0.0.1"; //localhost
        int port = 11111;
        Socket socket = new Socket(ip, port);
        BufferedReader input= new BufferedReader(new InputStreamReader(System.in));
        String textInput=null;
        while(!"Exit".equals(textInput)){
            textInput = input.readLine();
            if(!textInput.equals(null)) schreibeNachricht(socket, textInput);
            String empfangeneNachricht = leseNachricht(socket);
            System.out.println(empfangeneNachricht);
        }
    }
    void schreibeNachricht(Socket socket, String nachricht) throws IOException{
        PrintWriter printWriter =
                 new PrintWriter(
                  new OutputStreamWriter(
                     socket.getOutputStream()));
             printWriter.print(nachricht);
             printWriter.flush();
    }
    String leseNachricht(Socket socket) throws IOException{
        BufferedReader bufferedReader =
                 new BufferedReader(
                 new InputStreamReader(
                       socket.getInputStream()));
             char[] buffer = new char[200];
             int anzahlZeichen = bufferedReader.read(buffer, 0, 200); // blockiert bis Nachricht empfangen
             String nachricht = new String(buffer, 0, anzahlZeichen);
             return nachricht;
    }
}

ThreadKlasse:
Java:
public class ErwarteNachricht implements Runnable{
    Socket client;
    String nachricht;
   
    ErwarteNachricht(Socket vonSocket){
        this.client = vonSocket;
    }
    @Override
    public void run() {
        try {
            nachricht = leseNachricht(client);
        } catch (IOException e) {
            e.printStackTrace();
        }
       
    }
   
    String leseNachricht(Socket socket) throws IOException {
          BufferedReader bufferedReader =
             new BufferedReader(
              new InputStreamReader(
                 socket.getInputStream()));
         char[] buffer = new char[200];
         int anzahlZeichen = bufferedReader.read(buffer, 0, 200); // blockiert bis Nachricht empfangen
         String nachricht = new String(buffer, 0, anzahlZeichen);
         buffer = null;
         return nachricht;
    }
    boolean hatNachricht(){
        try{
            if(nachricht != null) return true;
        }catch (NullPointerException e){
            return false;
            //e.printStackTrace();
        }
        return false;
    }
    String getNachricht(){
        return nachricht;
    }
    void resetNachricht(){
        nachricht = null;
    }
}

Ich habe mich dabei an ein Tutorial gehalten und es versuchsweise ein wenig modifiziert..

Nun, sende ich von einem Client eine Nachricht, hängt er sich in der Methode NachrichtSchreiben in der Serverklasse auf. Solange bis ich im anderem Client eine Nachricht schreibe, dann gibt er mir erst in beiden Clients die Nachricht des im jeweilig anderem geschriebenem aus!

Nun, das verstehe ich nicht so recht, wie ich das anders hinbekomme! Vermutlich hängt er sich schon beim lesen auf und wartet auf bis von Serverseitens eine Antwort kommt, die aber nur kommen kann, wenn der andere Thread ebenfalls eine Nachricht eingelesen hat..

Naja, jedenfalls wäre ich erfreut wenn mir jemand diesen Sachverhalt erläutern könnte ;) ! Ich habe jetzt expliziet keine mir verständliche Erklärung, oder ein besseres Beispiel anderswo gefunden!

gruß
 

InfectedBytes

Top Contributor
schau dir mal die Kommentare in dem Code an...
Java:
 String leseNachricht(Socket socket) throws IOException{
        BufferedReader bufferedReader =
                 new BufferedReader(
                 new InputStreamReader(
                       socket.getInputStream()));
             char[] buffer = new char[200];
             int anzahlZeichen = bufferedReader.read(buffer, 0, 200); // blockiert bis Nachricht empfangen
             String nachricht = new String(buffer, 0, anzahlZeichen);
             return nachricht;
    }
Das Programm blockiert in jedem Schleifendurchlauf, bis eine Nachricht empfangen wurde.
Sinnvollerweise solltest du auch auf der Clientseite in einem separaten Thread blockieren.
Außerdem hast du tonnenweise doppelten Code, welchen du leicht auslagern könntest.
 

Tiding

Aktives Mitglied
Das habe ich auch schon probiert.. Klappte aber auch nicht. Wahrscheinlich habe ich bei der Thread erstellung was flasch gemacht?
Dieses Thema ist neu für mich, deswegen ist wohl alles etwas doppelt :'D

Ach oben meinte ich nicht beim Lesen, sondern beim Schreiben!
 

Tiding

Aktives Mitglied
Nun dann melde ich mich doch nocheinmal zu Wort:
Meine jetzige Struktur schaut so aus:

Server:
Java:
public class Server{
 
   String clientMsg;
 
   int clients;
  private final Scanner sc = new Scanner(System.in);
   private final int port = 11111;
   ThreadHandler th;
 
   //Client/Server
   private ClientHandler ch;
   private ServerSocket server;
   
   public static void main(String[] args){
     Server server = new Server();
   
     try {
       server.init();
     }catch (IOException e){
       e.printStackTrace();
     }
   }
   
   void init() throws IOException {
   
   
     //server
     server = new ServerSocket(port);

     //Client-joins and init
     ch = new ClientHandler(server);
     ch.start();
   
     //server-input
     th = new ThreadHandler(sc);

    //run it
    run();
   
    //closings
  /*System.out.println("Server shutdown");
  close();*/

   }
 
   void run(){
    while(!sc.nextLine().equals("Shutdown")){
       if(th.hasMsg())   {
         for(PrintWriter pw:ch.getClientOuts()){
           pw.println(th.getMsg());
           pw.flush();
         }
         th.resetMsg();
       }
       for(ThreadHandler in:ch.getClientIns()){
         if(in.hasMsg()){
           //System.out.println("in");
           System.out.println("Clientx : "+in.getMsg());
           clientMsg = in.getMsg();
           for(PrintWriter pw:ch.getClientOuts()){
             pw.println(clientMsg);
             pw.flush();
           }
           in.resetMsg();
         }
       }
    }
   }
}

Client:
Java:
public class Client{
 
  private BufferedReader in;
  private PrintWriter out;
  private final Scanner sc=new Scanner(System.in);
  private final String ip = "127.0.0.1";
   private final int port = 11111;
   ThreadHandler th, th_c;
 
   //Client
   private Socket client;
 
   //Main
   public static void main(String[] args){
     Client client = new Client();
     try{
       client.init();
     } catch (IOException e){
       e.printStackTrace();
     }
   }
 
   void init() throws IOException {
       
     //Client
     client = new Socket(ip, port);
     out = new PrintWriter(client.getOutputStream());
     in = new BufferedReader(new InputStreamReader(client.getInputStream()));

    //Threads
     th = new ThreadHandler(sc); //input
    th_c = new ThreadHandler(in); //console
   
    th.start();
    th_c.start();
   
    //run it
    run();
   
    //closings   
  /*System.out.println("Disconnected from server");
  close();*/
   }
 
   void run(){
    //while(!th.getMsg().equals("Exit")){
     while(true){
       if(th.hasMsg()){
         out.println(th.getMsg());
         out.flush();
         th.resetMsg();
       }
       if(th_c.hasMsg()){
         System.out.println("Server : "+th_c.getMsg());
         out.flush();
         th_c.resetMsg();
       }
    }
     //closings
   }

ThreadHandler:
Java:
public class ThreadHandler extends Thread{
 
   BufferedReader reader;
   Scanner scanner;
   String msg;
   String user;
   boolean running = true;
 
   ThreadHandler(BufferedReader reader){
     this.reader = reader;
   }
   ThreadHandler(Scanner scanner){
     this.scanner = scanner;
   }
 
   @Override
   public void run() {
     while(running){
       try {
         //System.out.println("jo!");
         if(reader != null)msg = reader.readLine();
         if(scanner != null)msg = scanner.nextLine();
       } catch (IOException e) {
         System.out.println("Unexpected error appeared...");
         e.printStackTrace();
       }
     }
   }
 
   //message to use
   boolean hasMsg(){
     try{
       if(!msg.equals(null))return true;
     }catch(NullPointerException e){
       return false;
     }
     return false;
   }
   String getMsg(){
     return msg;
   }
   String getUsername(){
     return user;
   }
   void resetMsg(){
     msg = null;
   }
 
   //running getter/setter
   boolean running(){
     return running;
   }
   void setRunning(boolean running){
     this.running = running;
   }

ClientHandler:
Java:
public class ClientHandler extends Thread{

   ServerSocket serverSocket;
   Socket client;
   LogWriter lw;
 
   LinkedList <ThreadHandler> ClientIns = new LinkedList<ThreadHandler>();
   LinkedList <PrintWriter> ClientOuts = new LinkedList<PrintWriter>();
 
   ClientHandler(ServerSocket serverSocket){
     this.serverSocket = serverSocket;
   }
 
   public void run(){   
     while(true){
       try {
         if((client = serverSocket.accept()) != null){
           System.out.println("Client: " + client.getLocalAddress() + " connected!");
           //out: PrintWriter
           ClientOuts.add(new PrintWriter(client.getOutputStream()));
           //in: InputStream in ThreadHandler
           ThreadHandler th = new ThreadHandler(new BufferedReader(new InputStreamReader(client.getInputStream())));
           th.start();
           ClientIns.add(th);
         }
       } catch (IOException e) {
         e.printStackTrace();
       }
     }
   }
 
   public LinkedList<ThreadHandler> getClientIns(){
     return ClientIns;
   }
   public LinkedList<PrintWriter> getClientOuts(){
     return ClientOuts;
   }
}

Mein jetziges Problem ist, dass meine Kommunikation nichtmehr funktioniert. Also sind denke ich mal nur die Klassen Server und ClientHandler wichtig zu betrachten.

Das connecten von mehreren Clients funktioniert wunderbar. Die Kommunikation also sprich: das senden von Nachrichten vom Client zum Server und vom Server zu allen Clients hat mit manueller Clientdeklarierung, also in der Serverklasse (Client1, Client2, Client3... dazu seperat ThreadHandler erstellt, etc) noch funktioniert.

Jetzt allerdings nichtmehr, evtl. hat ja jemand Spass daran mir zu helfen ;)!
 

Tiding

Aktives Mitglied
Hm, wenn ich nichts schreibe, die Clients connecte, dann schreibe, funktioniert es. Wenn ich allerdings dann einen weiteren Client connecte, hängt er sich auf:

Exception in thread "main" java.util.ConcurrentModificationException
at java.util.LinkedList$ListItr.checkForComodification(Unknown Source)
at java.util.LinkedList$ListItr.next(Unknown Source)
at structure.Server.run(Server.java:62)
at structure.Server.init(Server.java:45)
at structure.Server.main(Server.java:25)

An der Liste, dass das keine optimal-Lösung ist, ist mir klar... Allerdings verstehe ich den Fehler hier noch nicht wirklich.
 

Tiding

Aktives Mitglied
Aha, so wie ichs verstehe ist das hier also eine Sache der Synchronisation. Wenn mein ClientHandler also einen Client während der Listeniteration annimmt und infolge dessen der Liste ein neues Listenelement hinzufügt, nun ja ergibt Sinn.. ._.
 

Tiding

Aktives Mitglied
Java:
        if((client = serverSocket.accept()) != null){
           System.out.println("Client: " + client.getLocalAddress() + " connected!");
           //out: PrintWriter
           synchronized(this){
             ClientOuts.add(new PrintWriter(client.getOutputStream()));
             //in: InputStream in ThreadHandler
             ThreadHandler th = new ThreadHandler(new BufferedReader(new InputStreamReader(client.getInputStream())));
             th.start();
             ClientIns.add(th);
           }
         }

Ist das möglich? Wird nun auch der Server davon abgehalten, während dieser Code im Thread durchlaufen wird, auf die Listen zuzugreifen? Sprich muss er warten bis der Code durchlaufen ist, befor er mit seiner for-Iteration durch die Liste fortfahren darf?[/code]
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
ExceptionOfExpectation Server/Client-Kommunikation Netzwerkprogrammierung 34
I Client/Server Kommunikation bei einem Spiel Netzwerkprogrammierung 4
brainless Client Server Kommunikation verschlüsseln Netzwerkprogrammierung 13
P MIME-TYPE Erklaerung, Kommunikation zwischen Client und Server Netzwerkprogrammierung 3
J Sichere Kommunikation bei Server Client Netzwerkprogrammierung 3
M allgemeine Frage über Server-Client-Kommunikation Netzwerkprogrammierung 5
L Ratschlag zur Umsetzung einer client-server-Kommunikation Netzwerkprogrammierung 6
R Server zu Client Kommunikation Netzwerkprogrammierung 11
V Socket UDP Server/Client Kommunikation sehr langsam Netzwerkprogrammierung 2
F Socket Server/Client Kommunikation Netzwerkprogrammierung 4
X Problem mit Server-Client-Kommunikation Netzwerkprogrammierung 14
D Server-Client (Web) Kommunikation Netzwerkprogrammierung 9
E Client-Server-Kommunikation Netzwerkprogrammierung 13
C HTTP Studienarbeit Kommunikation via HTTP mit POST zwischen Server und Client Netzwerkprogrammierung 7
G Problem mit Client-Server Kommunikation Netzwerkprogrammierung 4
G unvollständige Daten: Http Client-Server-Kommunikation Netzwerkprogrammierung 2
J client/server kommunikation Netzwerkprogrammierung 3
M Client-Kommunikation ohne Server Netzwerkprogrammierung 7
S Kommunikation Fortran <-> Java auf Client-Server-Archi Netzwerkprogrammierung 2
G JINI über RMI // Client-Server Kommunikation Netzwerkprogrammierung 4
I Performanteste Kommunikationsmethode zwischen Client u. Server Netzwerkprogrammierung 4
L Socket Automatische Zuweisung von Server und Client Rolle Netzwerkprogrammierung 12
M Server-Client-System für Browsergame Netzwerkprogrammierung 5
Yonnig Threads mit Client/Server und GUI (laufend bis button-click) Netzwerkprogrammierung 9
J Client-Server und SOAP Netzwerkprogrammierung 23
L30nS RMI Aufruf einer Client-Methode von einem RMI-Server Netzwerkprogrammierung 3
T String von Client zu Server kommt nicht an Netzwerkprogrammierung 92
D WebSocket Server mit HTML Client und Java Server Netzwerkprogrammierung 5
D Server - Client Informationsaustausch, Möglichkeiten Netzwerkprogrammierung 3
H Socket Chat entwickeln mit Java Server Client Netzwerkprogrammierung 4
X Kann ich einen Client/Server verbindung hinkriegen die mir alle paar Sekunden die aktuellen Daten per Realtime zuschickt ? Netzwerkprogrammierung 9
D Slf4j - Logging - Client-Server Architektur Netzwerkprogrammierung 3
J client server mit nur einem PC Netzwerkprogrammierung 33
M Socket Nachricht von TCP-Client an Server schicken Netzwerkprogrammierung 12
M Socket Verbindung Matlab(Server) Java(Client) Netzwerkprogrammierung 1
R Socket FATAL EXCEPTION MAIN bei Socket based client/server app Netzwerkprogrammierung 2
G Server-Client IO Problem Netzwerkprogrammierung 6
I Socket Das erste Server-Client Programm Netzwerkprogrammierung 16
M Socket Server antwortet dem Client nicht Netzwerkprogrammierung 6
E Objekte versenden, Client-Server Netzwerkprogrammierung 25
C Mini Client-Server-Anwendung funktioniert nicht Netzwerkprogrammierung 8
P Server als Client nutzen Netzwerkprogrammierung 8
D Socket Run Args Client/Server Socket Netzwerkprogrammierung 1
Cromewell Socket Multithreaded Server und Client Netzwerkprogrammierung 1
Y Client/Server/DB communication Netzwerkprogrammierung 3
JavaWolf165 Socket mit .writeUtf etwas vom Client zum Server schicken Netzwerkprogrammierung 13
P RMI Client Server Programm über Internet Netzwerkprogrammierung 2
gamebreiti Socket Server / Client Anwendung Manipulation von Objekten durch Server Netzwerkprogrammierung 9
F Server Client Anwendung mit UDP Netzwerkprogrammierung 2
A RMI Wo treten Exceptions bei RMI Aufrufen auf? Auf Client oder auf Server? Netzwerkprogrammierung 3
A ByteBuffer - Client/Server Netzwerkprogrammierung 9
K C# Server - Android Client Netzwerkprogrammierung 0
T Frage zu Client-Server Applikation Netzwerkprogrammierung 2
H Socket Client/Server Socket Programmieren Netzwerkprogrammierung 1
M Theoretische Frage zu Server - Client Netzwerkprogrammierung 2
P HTTP Server / Client Netzwerkprogrammierung 1
E Thematik Client server Netzwerkprogrammierung 2
D Client/Server per Crossover Lan Kabel Netzwerkprogrammierung 1
S Client Server Connection Netzwerkprogrammierung 4
V erste Client - Server Anwendung, paar Fragen wie Socketverbindung checken usw. Netzwerkprogrammierung 4
S Sichere Server/Client Architektur Netzwerkprogrammierung 1
D Chat Server/mehre Client Netzwerkprogrammierung 9
I Server+Client Netzwerkprogrammierung 3
N Client am Server abmelden Netzwerkprogrammierung 0
F Server/Client Probleme Netzwerkprogrammierung 3
U Socket Instant Messanger (Server Linux, Client Windows) Netzwerkprogrammierung 1
Athena Grundsatzfragen zu Client-Server-Architektur / Matchmaking Netzwerkprogrammierung 1
A Problem beim Senden von Client zu Server Netzwerkprogrammierung 10
F Client Server DB Netzwerkprogrammierung 0
A Verständnisfrage Multi-Threaded Client/Server Netzwerkprogrammierung 5
F Tipps zum Thema Server/Client vie SOAP Netzwerkprogrammierung 0
F Socket Java - Server/Client simple Netzwerkprogrammierung 1
R Zeitliche Syncronisation Server - Client Netzwerkprogrammierung 0
S Server-Client: Image senden Netzwerkprogrammierung 2
C Multithreading Client / Server erklärt Netzwerkprogrammierung 11
P server - client verbindung (anfänger) Netzwerkprogrammierung 8
J Client Server - Serialisierung Netzwerkprogrammierung 8
Luk10 Server / Client: Clients speichern! Netzwerkprogrammierung 6
K Client => Server Netzwerkprogrammierung 2
A ? Home-Network, Server/Client-Einrichtung Netzwerkprogrammierung 4
S Socket Server: ConnectionError vom Client erkennen Netzwerkprogrammierung 31
A Java Server - IOS Client Applikation Netzwerkprogrammierung 20
M RMI RMI Probleme zwischen Client und Server Netzwerkprogrammierung 5
J Erster Server-Client läuft auf lokalem Rechner problemlos. Zwei Rechner über das Internet nicht Netzwerkprogrammierung 8
N Client-Server-Datenbank Netzwerkprogrammierung 13
Kjubert Synchronisieren von Objekten über Client/Server - bester Weg? Netzwerkprogrammierung 7
B Client/Server Connection Problem Netzwerkprogrammierung 2
S Server Client Daten hin und herschicken Netzwerkprogrammierung 2
D TCP Verbindung (Java Client und Visual Basic Server) Netzwerkprogrammierung 12
S Socket Applet Client bekommt keine GLOBALE Verbindung zum Server Netzwerkprogrammierung 25
T Server und Client verbinden nicht Netzwerkprogrammierung 6
D Server Client Verbindung - Unexpected End of File - Invalid HTTP Response Netzwerkprogrammierung 4
das-mo Client/Server sendet nicht Netzwerkprogrammierung 7
Z Socket Server/Client vernünftiger Verbindungsabbruch Netzwerkprogrammierung 4
G Bild über Socket schicken - Client/Server Netzwerkprogrammierung 10
F TCP Server/Client Netzwerkprogrammierung 14
M Problem Client - Server Sockets: .ready() wird nie true! Netzwerkprogrammierung 6
Ollek Socket Sucher passende Server/Client Lösung für meine Anwendung Netzwerkprogrammierung 2
N eine klasse mit server & client Netzwerkprogrammierung 5
D RMI Gui auf client updaten basierend auf den Property Änderung des Models auf dem Server ohne polling Netzwerkprogrammierung 12

Ähnliche Java Themen

Neue Themen


Oben