我正在使用java创建一个简单的Web代理应用程序。基本上,main方法创建一个RequestReceiver对象,该对象具有监听Web浏览器http请求的ServerSocket。从serverSocket.accept()返回的套接字创建一个新的Connection对象,并将其放入一个线程池中。
我遇到的问题是并非所有的http GET请求似乎都被serverSocket接收。例如,在我正在测试的一个网页上,我可以看到代理服务器只收到了10个GET请求中的7个。这会导致网页挂起并需要很长时间才能加载。什么可能导致带有serverSocket.accept()函数的线程在建立新连接时不总是优先执行?
RequestReceiver.java
public class RequestReceiver {
public static final int LISTENING_PORT = 4000;
public static final int CONNECTION_THREAD_POOL_SIZE = 30;
private ServerSocket serverSocket;
private ThreadPoolExecutor connectionThreads;
public RequestReceiver() throws IOException{
serverSocket = new ServerSocket(LISTENING_PORT);
connectionThreads = new ThreadPoolExecutor(CONNECTION_THREAD_POOL_SIZE, CONNECTION_THREAD_POOL_SIZE,
1000, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>());
}
public void start(){
try {
System.out.println("Current Pool Size: " + connectionThreads.getPoolSize()
+ " Active threads: " + connectionThreads.getActiveCount() );
Connection conn = new Connection(serverSocket.accept());
System.out.println("Created a new connection thread. Request from " + conn.clientSocketToString());
connectionThreads.execute(conn);
} catch (IOException e) {
System.err.println("Exception occured when accepting a new connection.");
e.printStackTrace();
}
}
}
Connection.java
public class Connection implements Runnable{
public static final int REPLY_CHUNK_SIZE = 32768;
public static final int DEFAULT_WEB_SERVER_PORT = 80;
public static final int SERVER_SOCKET_TIMEOUT = 0; // milliseconds
public static final int CLIENT_SOCKET_TIMEOUT = 0; // milliseconds
private Socket clientSocket, serverSocket;
private InputStream clientIS, serverIS;
private OutputStream clientOS, serverOS;
public Connection(Socket clientSocket){
this.clientSocket = clientSocket;
// set client socket timeout
try{
clientSocket.setSoTimeout(CLIENT_SOCKET_TIMEOUT);
}catch(SocketException soe){
soe.printStackTrace();
}
}
@Override
public void run() {
String connection = "";
try{
// setup client streams
clientIS = clientSocket.getInputStream();
clientOS = clientSocket.getOutputStream();
// get the request from the browser
String request = "";
String hostname = "";
String[] hostAndPort = new String[2];
request = browserInputStreamToString(clientIS);
hostname = getHostName(request);
hostAndPort = hostname.split(":");
connection = "Connection to: " + hostname + " from " + clientSocket.getInetAddress().getHostName()
+ ":" + clientSocket.getPort() + " Request: " + request.split(System.getProperty("line.separator"))[0];
System.out.println("OPENED>> " + connection);
// Attempt to create socket to server
serverSocket = new Socket(hostAndPort[0], (hostAndPort.length > 1 ? new Integer(hostAndPort[1]):DEFAULT_WEB_SERVER_PORT));
// set timeout
serverSocket.setSoTimeout(SERVER_SOCKET_TIMEOUT);
// Set up server streams
serverIS = serverSocket.getInputStream();
serverOS = serverSocket.getOutputStream();
// send client request to server
serverOS.write(request.getBytes());
serverOS.flush();
// send server response to client in chunks
byte[] reply = new byte[REPLY_CHUNK_SIZE];
int replyLength = serverIS.read(reply);
while( replyLength != -1 ){
clientOS.write(reply, 0, replyLength);
clientOS.flush();
replyLength = serverIS.read(reply);
}
// close sockets
clientSocket.close();
serverSocket.close();
}catch(Exception e){
e.printStackTrace();
} finally{
try {
if(clientSocket != null){
clientSocket.close();
}
if(serverSocket != null){
serverSocket.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
System.out.println("CLOSED>> " + connection);
}
编辑:从catch语句中删除了return语句
答案 0 :(得分:0)
当你说10分中的7分时,你的意思是你测试了10次或者几次并得到了这个速度?我问,因为默认队列大小是50,所以如果你经常测试,你可能会遇到队列问题。如果您还没有更改队列大小..
其他事情,也与队列大小有关。你有几个回报和try-caches。如果发生任何事情,你将无法达到你的联系关闭的程度。因此,当队列已满时,您将获得超时,直到当前连接关闭。其他相关问题,资源泄漏。