从服务器套接字java中的客户端获取数据

时间:2013-08-24 11:59:09

标签: java sockets serversocket

我正在创建一个执行以下任务的服务器应用程序

  • 接受来自客户端的连接
  • 将每个客户端连接处理为单独的线程
  • 从客户端
  • 接收数据
  • 将数据发送到客户端

我能够连接客户端但无法从客户端

接收数据

只有当客户端断开连接时才会在我的控制台中显示数据.. !!!

代码: -

public class ServerListener {

    public static void main(String[] args) {
        new ServerListener().startServer();
    }

    public void startServer() {
        final ExecutorService clientProcessingPool = Executors
                .newFixedThreadPool(10);

        Runnable serverTask = new Runnable() {
            @Override
            public void run() {
                try {
                    ServerSocket serverSocket = new ServerSocket(8000);
                    System.out.println("Waiting for clients to connect...");
                    while (true) {
                        Socket clientSocket = serverSocket.accept();
                        clientProcessingPool
                                .submit(new ClientTask(clientSocket));
                    }
                } catch (IOException e) {
                    System.err.println("Unable to process client request");
                    e.printStackTrace();
                }
            }
        };
        Thread serverThread = new Thread(serverTask);
        serverThread.start();
    }

    private class ClientTask implements Runnable {
        private final Socket clientSocket;

        private ClientTask(Socket clientSocket) {
            this.clientSocket = clientSocket;
        }

        @Override
        public void run() {
            System.out.println("Got a client !");
            try {
            /* Get Data From Client */
                BufferedReader reader = new BufferedReader(
                        new InputStreamReader(clientSocket.getInputStream()));
                String clientData = "";
                clientData = reader.readLine();
                System.out.println("Data From Client :" + clientData);

            /* Send Data To Client */

                //Code

                clientSocket.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

}

3 个答案:

答案 0 :(得分:7)

您的实施问题

BufferedReader#readLine

  

读取一行文字。一条线被认为是由换行符('\ n'),回车符('\ r')或回车符后面的任何一个终止。

换句话说,如果您的客户端没有发送\n\r字符,那么在由于断开连接而导致IOException被抛出之前,该方法不会结束。

解决方案

替换此代码:

BufferedReader reader = new BufferedReader(
                    new InputStreamReader(clientSocket.getInputStream()));
String clientData = "";
clientData = reader.readLine();

使用:

int red = -1;
byte[] buffer = new byte[5*1024]; // a read buffer of 5KiB
byte[] redData;
StringBuilder clientData = new StringBuilder();
String redDataText;
while ((red = clientSocket.getInputStream().read(buffer)) > -1) {
    redData = new byte[red];
    System.arraycopy(buffer, 0, redData, 0, red);
    redDataText = new String(redData,"UTF-8"); // assumption that client sends data UTF-8 encoded
    System.out.println("message part recieved:" + redDataText); 
    clientData.append(redDataText);
}
System.out.println("Data From Client :" + clientData.toString());

InputStream#read

  

从输入流中读取一些字节数并将它们存储到缓冲区数组b中。实际读取的字节数以整数形式返回。此方法将阻塞,直到输入数据可用,检测到文件结尾或抛出异常。

将在执行的确切时刻读取尽可能多的字节 - 它基本上是缓冲读取。由于这些是原始字节,因此converting them to String时必须知道其编码才能正确显示它们(即“UTF-8”部分)。如果客户端发送字节的encoding是其他的,您可能需要更改它以便在控制台输出中获得正确的文本。

我建议阅读官方教程:

答案 1 :(得分:1)

BufferedReader.readLine()仅在存在行尾或流结束时返回。确保客户端正在发送换行符,或使用不同的方式读取输入流,如:

int ch = 0;
while ((ch = instream.read()) >= 0) {
    // do sometyhing with the character off the input stream.
    System.out.println("Got byte " + ch);
}
// will get here when the input stream is closed.

答案 2 :(得分:0)

可能是您的ExecutorService(而不是?)被调用的问题。

尝试替代

clientProcessingPool.submit(new ClientTask(clientSocket));

BufferedReader reader = new BufferedReader(
    new InputStreamReader(clientSocket.getInputStream()));
String line;
while( (line = reader.readLine()) != null) // just read everything
   System.out.println(line);

看看你是否得到任何输出。