Tcp Socket: readine зависает, если используется в цикле while на клиенте: java

Я ломал голову, пытаясь понять, что происходит не так.

Я пытаюсь использовать простой серверный клиентский TCP-сокет в java. Сервер может отправить несколько строк в качестве ответа.
Я использую while((str = in.readLine())!= null) на стороне клиента, и он зависает после прочтения ответа. Пожалуйста, найдите код ниже. Я искал перед публикацией. Я удостоверяюсь, что заканчиваю ответ новой строкой.

Я пробовал комбинации \n, \r\n, но readLine не определяет конец строки.
Но на стороне сервера все работает нормально.

Пожалуйста помоги.

Спасибо.

СЕРВЕР:

import java.net.*;
import java.io.*;
public class SimpleServer {
public static void main(String args[]) throws IOException {

    ServerSocket s = new ServerSocket(55555);
    Socket socket = s.accept();

    BufferedReader in = new BufferedReader(
            new InputStreamReader(socket.getInputStream()));

    PrintWriter out = new PrintWriter(socket.getOutputStream(), true);

    String inputLine= null;
    System.out.println("call processInput"); 

       while ((inputLine = in.readLine()) != null) {
           System.out.println("before call processInput");           
           out.print("200 Success \r\n");
           out.flush();
           System.out.println("after call processInput: ");            
    }
    System.out.println("after while");
    out.close();
    in.close();
    socket.close();
    }
}

КЛИЕНТ:

import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.OutputStream;
import java.io.PrintWriter;
import java.net.Socket;
import java.net.UnknownHostException;
import java.nio.CharBuffer;

public class Test {
     public static void main(String[] args) throws IOException {

          try {

              System.out.println(":Connect");
                  Socket s = new Socket("192.168.1.114",55555);
                  System.out.println("Socket:" + s); 


                  System.out.println("after :Connect");



                  OutputStream s1out = s.getOutputStream();


                  PrintWriter output = new PrintWriter(s1out, true);   
                  output.println("login user root");
                  output.flush();


                  BufferedReader in = new BufferedReader(
                        new InputStreamReader(
                            s.getInputStream()));

                  System.out.println( in.readLine());



                  output.println("servershare");
                  output.flush();
                  System.out.println( "servershare");
                  String str = null;


             while((str = in.readLine())!= null) // hangs here
             {
                  System.out.println(str);

              }


               System.out.println( "share");
               output.println("share file1.txt file1.html, roopa ramesh");
                   str = null;
                   while((str = in.readLine())!= null && !str.equals(""))
                  System.out.println(str);

                  in.close();
                  output.close();
                  s.close();







          } catch (UnknownHostException e) {

                  // TODO Auto-generated catch block

                  e.printStackTrace();

          } catch (IOException e) {

                  // TODO Auto-generated catch block

                  e.printStackTrace();

          } 
     }
}

person Android_enthusiast    schedule 24.10.2011    source источник


Ответы (1)


У вас тупик:

  1. клиент отправляет логин
  2. сервер читает строку входа и отправляет 200 OK, и ждет следующей строки
  3. клиент читает 200 OK
  4. клиент отправляет servershare
  5. сервер читает строку servershare, отправляет 200 OK и ждет следующей строки
  6. клиент читает 200 OK и ждет следующей строки

И клиент, и сервер ждут следующей строки с другого конца. Ваш протокол неверен.

Кроме того, вы используете кодировку платформы по умолчанию на стороне сервера и на стороне клиента для чтения и записи сообщений. Если у клиента и сервера не одна и та же кодировка по умолчанию, у вас возникнут проблемы. Вы должны обернуть свои потоки средствами записи потоков ввода/вывода и указать конкретную кодировку при их создании.

person JB Nizet    schedule 24.10.2011
comment
Привет, протокол - это запрос или ответ, который должен заканчиваться на \r\n, и если он состоит из нескольких строк, каждая строка должна заканчиваться на \r. Также readline должен обнаруживать конец строки и выходить из нее, находясь на клиенте. Итак, если сервер отправляет несколько строк в качестве ответа, как прочитать его на стороне клиента без использования цикла while ??. Спасибо - person Android_enthusiast; 24.10.2011
comment
Метод readLine BufferedReader считает \r, \n и \r\n допустимыми концами строк. Вы должны читать char за char самостоятельно, если вам нужно сделать что-то другое для \r и \r\n. Более того, ваш цикл не останавливается при чтении строки. Он останавливается, когда readLine возвращает null, т.е. когда в потоке больше нечего читать. Единственный способ остановить этот цикл — закрыть выходной поток сервером. - person JB Nizet; 24.10.2011
comment
Привет спасибо. Но как мне проверить, является ли прочитанный символ \r\n, поскольку это два символа. Нужно ли мне помнить, что я читал ранее, и если за ним следует \n, подтверждать его \r\n. - person Android_enthusiast; 24.10.2011
comment
Извините, не могли бы вы уточнить. я не совсем понял. - person Android_enthusiast; 24.10.2011
comment
BufferedReader имеет методы пометки и сброса. Они могут быть полезны для реализации вашего протокола. Прочитайте их javadoc. - person JB Nizet; 24.10.2011