在客户端JAVA中调用socket.close()时套接字未关闭服务器端
我在使用 java 套接字时遇到问题。我有一个 ServerSocket
正在监听accept() 并为每个客户端请求生成线程。客户端和服务器之间的通信工作正常。我正在使用输入流从服务器线程中的客户端读取数据,例如:
inputStream = mySocket.getInputStream();
bytes = inputStream.read(buffer);
我的问题是,如果我从客户端调用 socket.close() ,则 bytes = inputStream.read(buffer) 的阻塞调用不会发生任何事情;
,它继续阻塞。但如果我从服务器关闭套接字,那么客户端的 inputStream.read(buffer); 就会返回“-1”。
服务器-主线程:
//SERVER MAIN THREAD, SPAWNS CLIENT THREADS
ServerSocket serverSocket = new ServerSocket(SERVERPORT);
while (listening){
new ServerThread(serverSocket.accept(), monitor).start();
}
服务器-客户端线程:
public class ServerThread extends Thread{
public ServerThread(Socket socket, Monitor monitor) {
this.socket = socket;
this.monitor = monitor;
}
public void run(){
byte[] buffer = new byte[1024];
int bytes;
//Listen
while(true){
try {
InputStream inputStream = socket.getInputStream();
monitor.doStuffWithOtherThreads(Object myObject);
bytes = inputStream.read(buffer); //Problem
if (bytes == -1){
System.out.println("breaks");
break;
}
byte[] readBuf = (byte[]) buffer;
String readMessage = new String(readBuf, 0, bytes);
System.out.println(readMessage);
System.out.println(bytes);
} catch (IOException e) {
System.out.println("Connection closed");
break;
}
}
}
客户端:
InetAddress serverAddr = InetAddress.getByName("serverhostname");
socket = new Socket(serverAddr, PORT);
socket.close(); //Close the socket connection from client. Nothing happens in the serverthread
I'm having problems with sockets in java. I have a ServerSocket
that is listening with accept() and spawns threads for each client-request. Communication between clients and the server works fine. I am using an inputstream to read data from clients in the serverthreads, like:
inputStream = mySocket.getInputStream();
bytes = inputStream.read(buffer);
My problem is that if I call socket.close() from the clients, nothing happens to the blocking call of bytes = inputStream.read(buffer);
, it continues to block. But it works if I close the socket from the server, then the inputStream.read(buffer);
of the client returns "-1".
SERVER-MAINTHREAD:
//SERVER MAIN THREAD, SPAWNS CLIENT THREADS
ServerSocket serverSocket = new ServerSocket(SERVERPORT);
while (listening){
new ServerThread(serverSocket.accept(), monitor).start();
}
SERVER-CLIENTTHREADS:
public class ServerThread extends Thread{
public ServerThread(Socket socket, Monitor monitor) {
this.socket = socket;
this.monitor = monitor;
}
public void run(){
byte[] buffer = new byte[1024];
int bytes;
//Listen
while(true){
try {
InputStream inputStream = socket.getInputStream();
monitor.doStuffWithOtherThreads(Object myObject);
bytes = inputStream.read(buffer); //Problem
if (bytes == -1){
System.out.println("breaks");
break;
}
byte[] readBuf = (byte[]) buffer;
String readMessage = new String(readBuf, 0, bytes);
System.out.println(readMessage);
System.out.println(bytes);
} catch (IOException e) {
System.out.println("Connection closed");
break;
}
}
}
CLIENT:
InetAddress serverAddr = InetAddress.getByName("serverhostname");
socket = new Socket(serverAddr, PORT);
socket.close(); //Close the socket connection from client. Nothing happens in the serverthread
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
您发布的服务器代码不检查-1。因此,要么这就是问题所在,要么这不是真正的代码,在这种情况下,您应该发布真实代码进行评论。
编辑您发布的代码的行为与您所描述的不同。
The server code you posted doesn't check for -1. So either that is the problem or that isn't the real code, in which case you should post the real code for comment.
EDIT The code you have posted does not behave as you have described.
在你的 Android 客户端代码中尝试一下:
应该会更好;-)
Try this in your Android client code :
It should be better ;-)
我不知道我是否理解你的问题,但我想说,由服务器关闭套接字是正常的。
在服务器端(在独立线程中),您有侦听套接字:
然后可能(在同一线程中,如果它是小型服务器)接受传入连接的循环(没有异常管理,可能socket.close位于finally块中) :
在客户端,您有:
服务器应该知道它何时到达请求末尾。例如在http中它可能是(取自scala中的mockHttpServer,因此可能会出现一些错误,但过程是相同的):
编辑:
我读了添加的代码,但仍然不明白:
你有3个“套接字”:
服务器打开和关闭监听和“接受”套接字,并且不应受到不良客户端套接字管理的影响。
然后,如果您希望服务器接受多个并发连接,您可以添加一个线程池来接受连接并处理请求和响应。
I don't know if I understand your issue, but I would say that it is normal that it's up to the server to close the socket.
On server side (in an independent thread) you have the listening socket :
Then probably (in the same thread if it is a small server) a loop accepting incoming connections (no exception management, probably the socket.close is in a finally block) :
On the client side, you have :
The server should know when it has reached the end of the request. For example in http it could be (taken from a mockHttpServer in scala so there might be some errors but the process is the same):
EDIT :
I read the code added and I still don't get it :
You have 3 "sockets" :
The server open and close listening and "accept" socket, and should have no impact of bad client socket management.
Then if you want your server to accept several concurrent connections, you may add a ThreadPool for accepting connections and treating requests and responses.