2015-02-25 4 views
0

Как проверить на стороне сервера, если сокет был закрыт на стороне клиента?Проверьте, закрыт ли клиентский сокет на сервере

У меня есть этот сервер, который ожидает затем соединение возврата 10 сообщений клиента:

public class SocketServidor { 
    static ServerSocket serverSocket; 

    public static void main(String[] args) throws Exception { 
     serverSocket = new ServerSocket(5963); 
     while(true) { 
      final Socket socket = serverSocket.accept(); 
      new Thread(() -> { 
       try { 
        PrintWriter out = new PrintWriter(socket.getOutputStream()); 
        for (int i = 0; i < 10; i++) { 
         int valor = (int) (Math.random() * 5) + 1; 
         out.println("Você acabou de ganhar R$ "+new DecimalFormat("###,##0.00").format(valor)+"!"); 
         out.flush(); 
         Thread.sleep(valor*1000); 
        } 
        socket.close(); 
       } catch (Exception ex) { 
        Logger.getLogger(SocketServidor.class.getName()).log(Level.SEVERE, null, ex); 
       } 
      }).start(); 
     } 
    } 
} 

И клиент, который только читает значения, но останавливается на пятом чтении:

public class SocketCliente { 

    public static void main(String[] args) throws Exception { 
     Socket socket = new Socket("localhost", 5963); 
     BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream())); 
     String leitura; 
     int lidas = 0; 
     while((leitura = in.readLine()) != null) { 
      lidas++; 
      System.out.println(leitura); 
      if(lidas == 5){ 
       socket.close(); 
      } 
     } 
    } 

} 

Проблема в том, что сервер продолжает отправлять сообщения клиенту даже после пятого чтения, когда клиент закрывает сокет. Как закрыть сокет на стороне сервера, когда клиент закрывает его на стороне?

+0

проверить мой ответ здесь http://stackoverflow.com/questions/28484032/detect-socket-is -closed-after-remote-application-is-closed-принудительно/28484091 # 28484091 –

+0

Я не вижу причины, чтобы иметь петлю на стороне сервера. Почему бы не переместить этот цикл клиенту и заставить клиента периодически запрашивать данные о сервере? –

ответ

0

Исключение подавляется PrintWriter.flush()
Вы не видите никаких исключений, потому что исключение подавляется PrintWriter.flush(). Чтобы проверить состояние ошибки после PrintWriter.println(), вы можете использовать PrintWriter.checkError() вместо flush(). В качестве альтернативы, вы можете использовать OutputStreamWriter вместо PrintWriter, тогда исключение не будет подавлено.

  1. С checkError

    serverSocket = new ServerSocket(5963); 
    while(true) { 
        final Socket socket = serverSocket.accept(); 
        new Thread(() -> { 
         try { 
          PrintWriter out = new PrintWriter(socket.getOutputStream()); 
          for (int i = 0; i < 10; i++) { 
           int valor = (int) (Math.random() * 5) + 1; 
           out.println("Você acabou de ganhar R$ "+new DecimalFormat("###,##0.00").format(valor)+"!"); 
           //out.flush(); 
           if(out.checkError()){ 
            System.out.println("Error. Break"); 
            break; 
           } 
           Thread.sleep(valor*1000); 
          } 
          socket.close(); 
         } catch (Exception ex) { 
          ex.printStackTrace(); 
         } 
        }).start(); 
    } 
    
  2. С OutputStreamWriter

    serverSocket = new ServerSocket(5963); 
    while(true) { 
        final Socket socket = serverSocket.accept(); 
        new Thread(() -> { 
         try { 
          Writer out = new OutputStreamWriter(socket.getOutputStream()); 
          for (int i = 0; i < 10; i++) { 
           int valor = (int) (Math.random() * 5) + 1; 
           out.write("Você acabou de ganhar R$ "+new DecimalFormat("###,##0.00").format(valor)+"!"); 
           out.write("\r\n"); 
           out.flush(); 
           Thread.sleep(valor*1000); 
          } 
          socket.close(); 
         } catch (Exception ex) { 
          ex.printStackTrace(); 
         } 
        }).start(); 
    } 
    
Смежные вопросы