0
如果Telnet客戶端斷開連接時沒有引發IOException,則會出現問題。當Telnet客戶端關閉時,BufferedReader或Socket不會引發異常
我使用的服務器代碼從以下來源:
http://java.sun.com/developer/onlineTraining/Programming/BasicJava2/Code/SocketThrdServer.java
從給定的代碼,服務器應該終止,並顯示「讀取失敗」當客戶密切。但是對於Telnet或Putty(RAW連接)不會發生這種情況。相反,它在我使用Client給出的示例時起作用,它完美地工作。
我也嘗試修改代碼,以便readLine()不總是阻止I/O,但使用超時。但是,它似乎並沒有幫助檢測客戶是否已斷開連接。
while (true) {
try {
client.setSoTimeout(1000);
line = in.readLine();
// Send data back to client
out.println(line);
textArea.append(line);
} catch (SocketTimeoutException ex) {
if(client.isClosed()) {
System.out.println("Client disconnected");
System.exit(-1);
}
} catch (Exception e) {
e.printStackTrace();
System.out.println("Read failed");
System.exit(-1);
}
}
使用Telnet或原始連接時是否存在缺失?
編輯:除此之外,當我運行2個客戶端,然後我關閉第一個客戶端,就沒有例外,從BufferedReader中拋出...
好吧,我想這就回答了這個問題。但是,我很好奇爲什麼優雅的關閉不會將套接字狀態設置爲關閉?這使得isClosed()無效,因爲套接字仍然認爲它沒有關閉...... –
嗯,我不確切地知道什麼是Close()符號,但是TCP連接只在* both * ends關閉連接時關閉(或者一個最終重置它,發送一個TCP RST)。 TCP連接可處於半雙工狀態,其中一端已關閉其寫入方向,但另一端仍可發送數據。 – nos
@Seeyabye TCP中沒有'撥號音',所以沒有辦法讓一個套接字知道另一端的套接字已經被關閉,而不是嘗試連接上的I/O。 'isClosed()'和朋友只告訴你你對自己的socket做了什麼,而不是連接發生了什麼。 – EJP