Java中从套接字读取时出现SocketException: Connection Reset?

3

在Java sockets方面遇到了一些烦人的问题,我的应用程序似乎在非常基本的层面上出现了故障。我的应用程序的一部分需要通过TCP连接写入文件名。接收者代码如下:

ServerSocket serverSocket = new ServerSocket(4445); 
Socket socket = serverSocket.accept();      
BufferedReader reader = new BufferedReader(
            new InputStreamReader(socket.getInputStream()));
String filename = reader.readLine();

我的发送方代码如下:

    Socket socket = new Socket(InetAddress.getLocalHost(), 4445);
    PrintWriter writer = new PrintWriter(socket.getOutputStream());
    writer.write("Test.jpg");

这里的内容非常基础,但是出现了一个套接字异常:Connection Reset,我运行了这个程序?以下是完整的堆栈跟踪:

Exception in thread "main" java.net.SocketException: Connection reset
at java.net.SocketInputStream.read(Unknown Source)
at sun.nio.cs.StreamDecoder.readBytes(Unknown Source)
at sun.nio.cs.StreamDecoder.implRead(Unknown Source)
at sun.nio.cs.StreamDecoder.read(Unknown Source)
at java.io.InputStreamReader.read(Unknown Source)
at java.io.BufferedReader.fill(Unknown Source)
at java.io.BufferedReader.readLine(Unknown Source)
at java.io.BufferedReader.readLine(Unknown Source)
at FileReceiver.main(FileReceiver.java:11)

问题出在FileReceiver.java文件的第11行,即reader.readLine()调用处。我无法弄清楚出了什么问题,之前我一直使用基本的TCP套接字都没有问题,为什么现在会发生这种情况?

6个回答

3
接收方正在等待行尾,但是发送方从未发送。请在发送端尝试使用类似println()的方法。

3
您的代码在我这里完全正常运行…您是否忘记添加

了?
    writer.close();
    socket.close();

你想将信息传达给你的作者吗?

2
你需要结合Nick和Nikolai所说的: 你需要用println写(因为readLine需要一个行末)并在关闭之前刷新你的写入器。
 Socket socket = new Socket(InetAddress.getLocalHost(), 4445);
 PrintWriter writer = new PrintWriter(socket.getOutputStream());
 writer.println("Test.jpg");
 writer.flush();

2
writer.close(); 不会刷新流吗? - Nikolai Fetissov
是的,我以为它被保留着以便进行额外的写入。 - Chris
我使用了 flush() 但是没有任何反应,请帮忙。 - Arsh Kaushal

1
我建议在尝试读取数据之前先清空你的写入器,因为有可能数据在你尝试读取之前从未被发送。

0

这是因为您的服务器退出了。使用while循环发送数据。请参见this。在此情况下,客户端尚未检索到数据时,服务器程序已退出,因此连接被重置并且您在客户端看到的异常被抛出。


0

克里斯是对的。当你使用 PrintWriter 或者像 ObjectOutputStream 这样的序列化时(ObjectOutputStream oos=new ObjectOutputStream(socket.getOutputStream());),你需要调用 .flush() 函数,并且在此之后必须关闭 Writer 和 socket。下面是你的解决方案:

 Socket socket = new Socket(InetAddress.getLocalHost(), 4445);
 PrintWriter writer = new PrintWriter(socket.getOutputStream());
 writer.println("Test.jpg");
 writer.flush();
 writer.close();
 socket.close();

以下是序列化的示例:(通过网络发送对象或将其保存到文件中以便将来进行复制)

    ...
ObjectOutputStream oos=new ObjectOutputStream(socket.getOutputStream());
oos.writeObject(record);
oos.flush();
oos.close();
socket.close();

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接