2017-02-17 4 views
2

Сервер:Отправка объектов через потоки для моего проекта не работает, сокет закрыт

public Server() throws IOException { 
    socket = new ServerSocket(PORT); 
    while (true) { 
     Socket client = socket.accept(); 
     Spooker.get().getWindow().append(client.getInetAddress().getHostAddress() + " has connected."); 
     if (inetAddrFound(client.getInetAddress().getHostName())) { 
      System.out.println("Address found."); 
      Thread thread = new Thread(new SpookerClient(client)); 
      threads.put(client, thread); 
      thread.start(); 
     } 

    } 

} 

private class SpookerClient implements Runnable { 

    Socket sock; 
    ObjectInputStream ois; 
    ObjectOutputStream oos; 

    public SpookerClient(Socket socket) { 
     System.out.println("Creating Spooker client."); 
     this.sock = socket; 
     try { 
      this.oos = new ObjectOutputStream(socket.getOutputStream()); 
      oos.flush(); 
      this.ois = new ObjectInputStream(socket.getInputStream()); 
     } catch (IOException e) { 
      e.printStackTrace(); 
     } 
    } 

    @Override 
    public void run() { 
     Client client; 
     try { 
      Spooker.get().getWindow().append("Finding object."); 
      System.out.println("Finding object."); 
      while ((client = (Client) ois.readObject()) != null && !Thread.currentThread().isInterrupted()) { 
       System.out.println("Object found."); 
       Spooker.get().getWindow().append("Object found."); 
       if (keyFound(client.getKEY()) && idFound(client.getID())) { 
        Spooker.get().getWindow().append("Writing object."); 
        System.out.println("Writing object."); 
        oos = new ObjectOutputStream(sock.getOutputStream()); 
        oos.writeObject(Spooker.get().getConfiguration()); 
        oos.flush(); 
        threads.remove(sock); 
        Thread.currentThread().interrupt(); 
       } 
      } 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
    } 
} 

Клиент:

public ClientConnection() { 
    try { 
     socket = new Socket(decode(ADDR), Integer.parseInt(decode(PORT))); 
     oos = new ObjectOutputStream(socket.getOutputStream()); 
     ois = new ObjectInputStream(socket.getInputStream()); 
     oos.writeObject(new Client()); 
     oos.flush(); 
     oos.close(); 
     Thread thread = new Thread(new IncomingSpookerConfiguration()); 
     thread.start(); 
    } catch (IOException e) { 
     e.printStackTrace(); 
    } 
} 

private class IncomingSpookerConfiguration implements Runnable { 

    SpookerConfiguration configuration; 

    @Override 
    public void run() { 
     System.out.println("Trying.."); 
     try { 
      while ((configuration = (SpookerConfiguration) ois.readObject()) != null && !Thread.currentThread().isInterrupted() && Spooker.get().getConfiguration() == null) { 
       System.out.println("Configuration loaded."); 
       Spooker.get().setConfiguration((SpookerConfiguration) ois.readObject()); 
       Thread.currentThread().interrupt(); 
       System.out.println(Spooker.get().getConfiguration().getX()); 
       socket.close(); 
      } 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
    } 
} 

Я получаю ошибку, что сокет закрыт. Я не понимаю, почему.

То, что я пытаюсь сделать, это;

Клиент отправляет сервер классу Client, который содержит уникальный идентификатор (CPUID, также found here). Сервер проверяет, зарегистрирован ли клиент - например, если их cpuid находится в базе данных.

Если cpuid находится в базе данных, сервер отправляет обратно класс SpookerConfiguration, который по существу будет классом, содержащим значения, которые клиент будет использовать для создания графического интерфейса (например, размер, заголовок, по умолчанию close op и т. Д.). .).

Что я делаю неправильно?

EDIT: ошибка

Client error: 

Trying.. 
java.net.SocketException: socket closed 
at java.net.SocketInputStream.socketRead0(Native Method) 
at java.net.SocketInputStream.socketRead(SocketInputStream.java:116) 
at java.net.SocketInputStream.read(SocketInputStream.java:171) 
at java.net.SocketInputStream.read(SocketInputStream.java:141) 
at java.net.SocketInputStream.read(SocketInputStream.java:224) 
at java.io.ObjectInputStream$PeekInputStream.peek 
(ObjectInputStream.java:2584) 
at java.io.ObjectInputStream$BlockDataInputStream.peek 
(ObjectInputStream.java:2891) 
at java.io.ObjectInputStream$BlockDataInputStream.peekByte 
(ObjectInputStream.java:2901) 
at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1502) 
at java.io.ObjectInputStream.readObject(ObjectInputStream.java:422) 
at com.spooker.connection.ClientConnection$IncomingSpookerConfiguration.run 
(ClientConnection.java:50) 
at java.lang.Thread.run(Thread.java:745) 

Сервер:

java.net.SocketException: 
Software caused connection abort: socket write error 
at java.net.SocketOutputStream.socketWrite0(Native Method) 
at java.net.SocketOutputStream.socketWrite(SocketOutputStream.java:111) 
at java.net.SocketOutputStream.write(SocketOutputStream.java:155) 
at java.io.ObjectOutputStream$BlockDataOutputStream.drain 
(ObjectOutputStream.java:1877) 
at java.io.ObjectOutputStream$BlockDataOutputStream.setBlockDataMode 
(ObjectOutputStream.java:1786) 
at java.io.ObjectOutputStream.writeFatalException 
(ObjectOutputStream.java:1580) 
at java.io.ObjectOutputStream.writeObject(ObjectOutputStream.java:351) 
at com.spooker.server.Server$SpookerClient.run(Server.java:65) 
at java.lang.Thread.run(Thread.java:745) 
+0

Пожалуйста, отредактируйте ваше сообщение и включите полную трассировку стека с обеих сторон. –

+0

Множество вещей; это начинается с того факта, что вы пишете довольно сложный, трудно читаемый код. Он начинается с таких вещей, как: почему вы создаете ** новые ** потоки объектов; хотя вы уже создали некоторые из классов классов? Почему вы смешиваете интерфейс с этим кодом? Дело в том, что вы много работали над написанием кода, который хорошо скрывает то, что он * действительно делает. На самом деле не удивительно, что вы теперь смотрите на других людей, чтобы понять, что делает ваш код ... – GhostCat

+0

@GhostCat Я смешиваю работу пользовательского интерфейса, так что людям сложно взломать мое программное обеспечение - так что если они «удаляют» процесс аутентификации (подключение к серверу), программное обеспечение не будет иметь значения GUI (строки, ints, booleans и т. д.), чтобы создать себя. Просто мера безопасности. – Archie

ответ

1
  1. socket closedозначает, что вы закрыл сокет, а затем продолжали использовать его. Решение: не надо.

  2. readObject() не возвращает нуль в конце потока. Он бросает EOFException. Неправильные петли чтения.

  3. Вы должны использовать те же потоки объектов в течение всего срока службы сокета.

Смежные вопросы