Java 中的 BufferedReader 在尝试从已关闭的套接字中读取时无法触发异常
BufferedReader in Java fails to trigger exception when trying to read from closed socket
我正在连接一个 TCP 套接字,并在该套接字的线程中为 I/O 打开一个缓冲的 reader,然后在缓冲的 reader 上使用 readLine 读取数据:
try {
socket = new Socket(targetHost, targetPort);
ou = new PrintWriter(socket.getOutputStream(), true);
in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
while (true) {
message = in.readLine();
...
process the data
...
}
} catch (Exception e) {
e.printStackTrace();
return;
}
只要有连接就可以正常工作。但是当 TCP 连接的另一端意外断开时,在大约 75% 的情况下,该线程永远不会意识到另一端已经断开,并且任何从缓冲的 reader 中读取的尝试都会简单地产生一个 "null" 字符串,但没有抛出异常,我无法关闭线程,因为它不知道另一端已经消失了。在大约 25% 的情况下,线程被终止(也没有产生异常),但这会产生预期的结果,我只需要线程在 TCP 连接断开时消失。
我尝试使用它来确定连接是否存在:
boolean connected = socket.isConnected() && !socket.isClosed();
但这行不通,总是 returns 当另一边已经离开并且线程继续咀嚼时为真。
有什么想法吗?
重点基本上是:"works as designed".
返回null的reader其实就是:"no more data; I am done here".
参见javadoc:
Returns:包含行内容的字符串,不包括任何行终止字符,如果已到达流末尾则为 null
换句话说:关闭套接字在这里被视为"normal"操作;因此也不例外。换句话说:您必须更改代码以检查结果是否为 readLine()
returns null;如果是这样,您就知道插座不见了。
我正在连接一个 TCP 套接字,并在该套接字的线程中为 I/O 打开一个缓冲的 reader,然后在缓冲的 reader 上使用 readLine 读取数据:
try {
socket = new Socket(targetHost, targetPort);
ou = new PrintWriter(socket.getOutputStream(), true);
in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
while (true) {
message = in.readLine();
...
process the data
...
}
} catch (Exception e) {
e.printStackTrace();
return;
}
只要有连接就可以正常工作。但是当 TCP 连接的另一端意外断开时,在大约 75% 的情况下,该线程永远不会意识到另一端已经断开,并且任何从缓冲的 reader 中读取的尝试都会简单地产生一个 "null" 字符串,但没有抛出异常,我无法关闭线程,因为它不知道另一端已经消失了。在大约 25% 的情况下,线程被终止(也没有产生异常),但这会产生预期的结果,我只需要线程在 TCP 连接断开时消失。
我尝试使用它来确定连接是否存在:
boolean connected = socket.isConnected() && !socket.isClosed();
但这行不通,总是 returns 当另一边已经离开并且线程继续咀嚼时为真。
有什么想法吗?
重点基本上是:"works as designed".
返回null的reader其实就是:"no more data; I am done here".
参见javadoc:
Returns:包含行内容的字符串,不包括任何行终止字符,如果已到达流末尾则为 null
换句话说:关闭套接字在这里被视为"normal"操作;因此也不例外。换句话说:您必须更改代码以检查结果是否为 readLine()
returns null;如果是这样,您就知道插座不见了。