OS之後的BindException:於Linux(Debian)
的Java:Java(商標)SE運行時環境(建立1.7.0_05-B06)
的Java:Java的熱點(TM )64位服務器VM(建設23.1 - B03,混合模式)
Apache的HTTP客戶端:v4.2.3(最新)的Apache HTTP客戶端 - >本地地址綁定 - >一段時間
我想創建一個PoolingConnectionManager有幾個客戶,各有其獨特的本地地址(ConnRoutePNames。 LOCAL_ADDRESS)。
這些客戶端將被幾個工作者使用(每個工作者選擇隨機客戶端並執行請求)。
的問題是:當我設置本地地址的客戶,一段時間後(例如1分鐘),我總是與消息「地址已在使用」得到java.net.BindException。
問題:它有問題嗎?
java.net.BindException: Address already in use
at java.net.PlainSocketImpl.socketBind(Native Method) ~[na:1.7.0_05]
at java.net.AbstractPlainSocketImpl.bind(AbstractPlainSocketImpl.java:376) ~[na:1.7.0_05]
at java.net.Socket.bind(Socket.java:627) ~[na:1.7.0_05]
at org.apache.http.conn.scheme.PlainSocketFactory.connectSocket(PlainSocketFactory.java:120) ~[httpclient-4.2.3.jar:4.2.3]
at org.apache.http.impl.conn.DefaultClientConnectionOperator.openConnection(DefaultClientConnectionOperator.java:180) ~[httpclient-4.2.3.jar:4.2.3]
at org.apache.http.impl.conn.ManagedClientConnectionImpl.open(ManagedClientConnectionImpl.java:294) ~[httpclient-4.2.3.jar:4.2.3]
at org.apache.http.impl.client.DefaultRequestDirector.tryConnect(DefaultRequestDirector.java:645) ~[httpclient-4.2.3.jar:4.2.3]
at org.apache.http.impl.client.DefaultRequestDirector.execute(DefaultRequestDirector.java:480) ~[httpclient-4.2.3.jar:4.2.3]
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:906) ~[httpclient-4.2.3.jar:4.2.3]
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:805) ~[httpclient-4.2.3.jar:4.2.3]
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:784) ~[httpclient-4.2.3.jar:4.2.3]
at controllers.Test$Worker.run(Test.java:67) ~[test_2.9.1-1.0-SNAPSHOT.jar:1.0-SNAPSHOT]
at java.lang.Thread.run(Thread.java:722) [na:1.7.0_05]
代碼(簡化):
public static void main(String[] args) throws UnknownHostException
{
ClientConnectionManager connManager = buildConnectionManager(30);
List<HttpClient> clients = new ArrayList<>();
for(int i=0; i<8; ++i)
{
HttpClient client = buildClient(connManager, InetAddress.getByName("111.111.111." + (50 + i));
clients.add(client);
}
for(int i=0; i<30; ++i)
{
new Thread(new Worker(clients)).start();
}
}
public static ClientConnectionManager buildConnectionManager(Integer parallelism)
{
PoolingClientConnectionManager connectionManager = new PoolingClientConnectionManager();
connectionManager.setMaxTotal(parallelism);
connectionManager.setDefaultMaxPerRoute(parallelism);
return connectionManager;
}
public static HttpClient buildClient(ClientConnectionManager connectionManager, InetAddress localAddress)
{
DefaultHttpClient httpClient = new DefaultHttpClient(connectionManager);
HttpParams params = httpClient.getParams();
params.setParameter(ConnRoutePNames.LOCAL_ADDRESS, localAddress);
return httpClient;
}
private static class Worker implements Runnable
{
private List<HttpClient> clients = null;
public Worker(List<HttpClient> clients)
{
this.clients = clients;
}
public void run()
{
do
{
HttpGet httpGet = new HttpGet("http://google.com/robots.txt");
HttpClient client = this.clients.get(new Random().nextInt(this.clients.size()));
try
{
HttpResponse httpResponse = client.execute(httpGet);
EntityUtils.consume(httpResponse.getEntity());
logger.debug("Success request");
}
catch(IOException e)
{
httpGet.abort();
logger.info("IO error", e);
}
}
while(true);
}
}
消耗響應後嘗試'httpResponse.releaseConnection()'。理想情況下,在如[所示](http://hc.apache.org/httpcomponents-client-ga/quickstart.html) – Pyranja
@Pyranja所示的finally塊中,不,它不起作用。無論如何,這不會很好的解決我的問題:( –