gpt4 book ai didi

java - 断开套接字与服务器的连接

转载 作者:行者123 更新时间:2023-12-02 11:26:11 28 4
gpt4 key购买 nike

我正在尝试通过创建套接字并将其连接到服务器、发送消息并关闭套接字(通过服务器的 close 方法)来测试我的聊天客户端应用程序。但是,当我关闭套接字时,客户端线程似乎仍在等待客户端输入。不过,我已经添加了 if 子句来阻止它等待。这是我的测试:

   @Test
public void testMessagesReceived() throws IOException
{
ServerSocket s = server.getSocket();
System.out.println(s);
mysocket = new Socket("127.0.0.1", 3000);

final PrintWriter stream = new PrintWriter(mysocket.getOutputStream(), true);

stream.println("Default room");

}
@AfterSuite
public void stopServer() {
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
server.stop();
}

但是,当 server.stop() 执行并关闭套接字时,我在客户端线程中遇到异常,该线程处于 Activity 状态并使用此套接字,如下所示:

 public void acceptFromConsole() throws IOException {

if (!socket.isClosed()) {


final BufferedReader fromClient = new BufferedReader(new InputStreamReader(socket.getInputStream()));

String message;
while ((message = fromClient.readLine()) != null) { // Exception here
if (message.contains(TelnetUtilities.Quit.toString())) {
room.removeClient(id);
break;
}
}

这是完整的堆栈跟踪:

   java.net.SocketException: Socket closed
at java.net.SocketInputStream.socketRead0(Native Method)
at java.net.SocketInputStream.socketRead(Unknown Source)
at java.net.SocketInputStream.read(Unknown Source)
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 com.egt.chat.server.ClientContainer.acceptFromConsole(ClientContainer.java:40)
at com.egt.chat.server.ClientContainerRunnable.run(ClientContainerRunnable.java:28)
at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
at java.lang.Thread.run(Unknown Source)

在我看来,在一个线程中我关闭了套接字,但是客户端线程看不到套接字上的更改,并且检查 if(!socket.isClosed()) 返回 true 并且执行流程继续并且当我尝试读取它时,当然会引发我试图从关闭的套接字读取的异常,有没有办法克服这个问题?

最佳答案

您的代码正在正常工作。当您强制断开套接字时,您的代码是 while 循环:

  while ((message = fromClient.readLine()) != null) { // Exception here
if (message.contains(TelnetUtilities.Quit.toString())) {
room.removeClient(id);
break;
}

readLine() 正在等待传入数据。如果您不关闭连接,它将永远等待新数据。然后,您关闭连接,readLine()(或者更好的是底层 socketRead 方法)现在识别出它无法从关闭的套接字读取数据并引发异常。

因此,此时此异常是预期的异常。捕获它并快乐起来。

我会这样做:添加一个 boolean 变量,例如 stopServerCalled ,默认情况下为 false ,并在 时设置为 true >stopServer() 被调用。

try {
while ((message = fromClient.readLine()) != null) { // Exception here
if (message.contains(TelnetUtilities.Quit.toString())) {
room.removeClient(id);
break;
}
} catch (SocketException e) {
// check if this is an expected exception and if yes ignore it
if (!stopServerCalled)
throw e;
}

关于java - 断开套接字与服务器的连接,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49612601/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com