在单独的线程中创建ServerSocket?
我在我的应用程序中使用ServerSocket
时遇到问题。在单独的线程中创建ServerSocket?
我在我的应用程序的构造函数中创建了ServerSocket
。套接字的构造函数调用accept()
方法来等待客户端连接。
问题是,accept()
方法冻结我的整个应用程序,直到客户端连接。所以我想问一下,是否有另一种方法可以在单独的线程中创建整个ServerSocket
,ServerSocket
及其accept()
方法的构造函数在我的主应用程序旁边调用?
编辑:
感谢奥利弗的意见,把。接受成可运行和创建线程池来处理clientconnections。
,现在这就是我的代码:
public void start(){
final ExecutorService clientProcessingPool = Executors.newFixedThreadPool(10);
Runnable serverTask = new Runnable() {
@Override
public void run() {
try {
serverSocket = new ServerSocket(port);
while (true) {
Socket clientSocket = serverSocket.accept();
objectout = new ObjectOutputStream(clientSocket.getOutputStream());
clientProcessingPool.submit(new ClientTask(clientSocket,objectout));
}
} catch (IOException e) {
System.err.println("Accept failed.");
}
}
};
万物运行良好!谢谢!
通常情况下,我使用N + 1个线程:ServerSocket,避免阻塞整个应用程序等待客户端连接;和N个线程来处理客户端的请求,N是线程池的大小(我建议使用线程池来为每个客户端创建一个新线程)。
下面是一个例子(只是编码,你可能希望有更好的异常管理等,但这个是最小的工作示例)
public class Server {
public static void main(String[] args) {
new Server().startServer();
}
public void startServer() {
final ExecutorService clientProcessingPool = Executors.newFixedThreadPool(10);
Runnable serverTask = new Runnable() {
@Override
public void run() {
try {
ServerSocket serverSocket = new ServerSocket(8000);
System.out.println("Waiting for clients to connect...");
while (true) {
Socket clientSocket = serverSocket.accept();
clientProcessingPool.submit(new ClientTask(clientSocket));
}
} catch (IOException e) {
System.err.println("Unable to process client request");
e.printStackTrace();
}
}
};
Thread serverThread = new Thread(serverTask);
serverThread.start();
}
private class ClientTask implements Runnable {
private final Socket clientSocket;
private ClientTask(Socket clientSocket) {
this.clientSocket = clientSocket;
}
@Override
public void run() {
System.out.println("Got a client !");
// Do whatever required to process the client's request
try {
clientSocket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
使用线程池处理客户端,您如何处理接收和发送数据到客户端和从客户端发送数据?我几周前看到的一个解决方案是Hanlder也有2个线程,一个用于发送,另一个用于接收数据。 – Loki 2013-03-21 07:40:04
此外,对于这个主题非常类似但稍微更具描述性的内容,请参阅以下文章:[http://tutorials.jenkov.com/java-multithreaded-servers/thread-pooled-server.html](http: //tutorials.jenkov.com/java-multithreaded-servers/thread-pooled-server.html) – 2015-05-12 12:37:40
这段代码并不能帮助抵御拒绝服务攻击,其中[accept](http://man7.org/linux/ man-pages/man2/accept.2.html)被攻击者阻止(或限制)。这样的攻击者会阻止你的服务器接受新的客户端。 – 2016-11-17 15:14:40
试图在单独的线程移动插座相关的代码?任何具体的问题面临? – Ankit 2013-03-21 07:43:41
查看java.nio.channels.AsynchronousServerSocketChannel并查看它是否符合您的要求。 – Crollster 2013-03-21 07:47:31
还是更好,请看看这个问题:http://stackoverflow.com/questions/8940747/how-should-i-use-asynchronousserversocketchannel-for-accepting-connections – Crollster 2013-03-21 07:49:17