HTTPCLIENT-948: Completed refactoring of the idle connection handling code; cleaned up logging in connection management code
git-svn-id: https://svn.apache.org/repos/asf/httpcomponents/httpclient/trunk@954903 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
11b94cdb86
commit
4b73b9c74e
|
@ -1,10 +1,14 @@
|
||||||
Changes since 4.1 ALPHA2
|
Changes since 4.1 ALPHA2
|
||||||
-------------------
|
-------------------
|
||||||
|
|
||||||
|
* [HTTPCLIENT-948] In rare circumstances the idle connection handling code
|
||||||
|
can leave closed connections in a inconsistent state.
|
||||||
|
Contributed by Oleg Kalnichevski <olegk at apache.org>
|
||||||
|
|
||||||
* [HTTPCLIENT-953] IllegalStateException thrown by RouteSpecificPool.
|
* [HTTPCLIENT-953] IllegalStateException thrown by RouteSpecificPool.
|
||||||
Contributed by Guillaume <gueugaie at gmail.com>
|
Contributed by Guillaume <gueugaie at gmail.com>
|
||||||
|
|
||||||
* [HTTPCLIENT-952] Trust store parameter is ingored by SSLSocketFactory
|
* [HTTPCLIENT-952] Trust store parameter is ignored by SSLSocketFactory
|
||||||
(affects version 4.1-alpha2 only)
|
(affects version 4.1-alpha2 only)
|
||||||
Contributed by Oleg Kalnichevski <olegk at apache.org>
|
Contributed by Oleg Kalnichevski <olegk at apache.org>
|
||||||
|
|
||||||
|
|
|
@ -468,15 +468,16 @@ public class DefaultRequestDirector implements RequestDirector {
|
||||||
if (reuse) {
|
if (reuse) {
|
||||||
// Set the idle duration of this connection
|
// Set the idle duration of this connection
|
||||||
long duration = keepAliveStrategy.getKeepAliveDuration(response, context);
|
long duration = keepAliveStrategy.getKeepAliveDuration(response, context);
|
||||||
managedConn.setIdleDuration(duration, TimeUnit.MILLISECONDS);
|
|
||||||
|
|
||||||
if (this.log.isDebugEnabled()) {
|
if (this.log.isDebugEnabled()) {
|
||||||
|
String s;
|
||||||
if (duration >= 0) {
|
if (duration >= 0) {
|
||||||
this.log.debug("Connection can be kept alive for " + duration + " ms");
|
s = duration + " " + TimeUnit.MILLISECONDS;
|
||||||
} else {
|
} else {
|
||||||
this.log.debug("Connection can be kept alive indefinitely");
|
s = "ever";
|
||||||
}
|
}
|
||||||
|
this.log.debug("Connection can be kept alive for " + s);
|
||||||
}
|
}
|
||||||
|
managedConn.setIdleDuration(duration, TimeUnit.MILLISECONDS);
|
||||||
}
|
}
|
||||||
|
|
||||||
RoutedRequest followup = handleResponse(roureq, response, context);
|
RoutedRequest followup = handleResponse(roureq, response, context);
|
||||||
|
|
|
@ -237,7 +237,6 @@ public class ConnPoolByRoute extends AbstractConnPool { //TODO: remove dependenc
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getConnectionsInPool(HttpRoute route) {
|
public int getConnectionsInPool(HttpRoute route) {
|
||||||
|
|
||||||
poolLock.lock();
|
poolLock.lock();
|
||||||
try {
|
try {
|
||||||
// don't allow a pool to be created here!
|
// don't allow a pool to be created here!
|
||||||
|
@ -330,9 +329,9 @@ public class ConnPoolByRoute extends AbstractConnPool { //TODO: remove dependenc
|
||||||
}
|
}
|
||||||
|
|
||||||
if (log.isDebugEnabled()) {
|
if (log.isDebugEnabled()) {
|
||||||
log.debug("[" + route + "] kept alive: " + freeConnections.size() +
|
log.debug("[" + route + "] total kept alive: " + freeConnections.size() +
|
||||||
", issued: " + leasedConnections.size() +
|
", total issued: " + leasedConnections.size() +
|
||||||
", allocated: " + numConnections + " out of " + maxTotalConnections);
|
", total allocated: " + numConnections + " out of " + maxTotalConnections);
|
||||||
}
|
}
|
||||||
|
|
||||||
// the cases to check for:
|
// the cases to check for:
|
||||||
|
@ -407,7 +406,6 @@ public class ConnPoolByRoute extends AbstractConnPool { //TODO: remove dependenc
|
||||||
poolLock.unlock();
|
poolLock.unlock();
|
||||||
}
|
}
|
||||||
return entry;
|
return entry;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -435,9 +433,14 @@ public class ConnPoolByRoute extends AbstractConnPool { //TODO: remove dependenc
|
||||||
|
|
||||||
if (reusable) {
|
if (reusable) {
|
||||||
if (log.isDebugEnabled()) {
|
if (log.isDebugEnabled()) {
|
||||||
|
String s;
|
||||||
|
if (validDuration >= 0) {
|
||||||
|
s = validDuration + " " + timeUnit;
|
||||||
|
} else {
|
||||||
|
s = "ever";
|
||||||
|
}
|
||||||
log.debug("Pooling connection" +
|
log.debug("Pooling connection" +
|
||||||
" [" + route + "][" + entry.getState() + "]" +
|
" [" + route + "][" + entry.getState() + "]; keep alive for " + s);
|
||||||
"; keep alive for " + validDuration + " " + timeUnit.toString());
|
|
||||||
}
|
}
|
||||||
rospl.freeEntry(entry);
|
rospl.freeEntry(entry);
|
||||||
entry.updateExpiry(validDuration, timeUnit);
|
entry.updateExpiry(validDuration, timeUnit);
|
||||||
|
@ -452,10 +455,7 @@ public class ConnPoolByRoute extends AbstractConnPool { //TODO: remove dependenc
|
||||||
} finally {
|
} finally {
|
||||||
poolLock.unlock();
|
poolLock.unlock();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} // freeEntry
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* If available, get a free pool entry for a route.
|
* If available, get a free pool entry for a route.
|
||||||
|
@ -485,7 +485,7 @@ public class ConnPoolByRoute extends AbstractConnPool { //TODO: remove dependenc
|
||||||
if (entry.isExpired(System.currentTimeMillis())) {
|
if (entry.isExpired(System.currentTimeMillis())) {
|
||||||
// If the free entry isn't valid anymore, get rid of it
|
// If the free entry isn't valid anymore, get rid of it
|
||||||
// and loop to find another one that might be valid.
|
// and loop to find another one that might be valid.
|
||||||
if(log.isDebugEnabled())
|
if (log.isDebugEnabled())
|
||||||
log.debug("Closing expired free connection"
|
log.debug("Closing expired free connection"
|
||||||
+ " [" + rospl.getRoute() + "][" + state + "]");
|
+ " [" + rospl.getRoute() + "][" + state + "]");
|
||||||
closeConnection(entry);
|
closeConnection(entry);
|
||||||
|
@ -510,7 +510,6 @@ public class ConnPoolByRoute extends AbstractConnPool { //TODO: remove dependenc
|
||||||
} finally {
|
} finally {
|
||||||
poolLock.unlock();
|
poolLock.unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
return entry;
|
return entry;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -591,12 +590,9 @@ public class ConnPoolByRoute extends AbstractConnPool { //TODO: remove dependenc
|
||||||
* Used to replace pool entries with ones for a different route.
|
* Used to replace pool entries with ones for a different route.
|
||||||
*/
|
*/
|
||||||
protected void deleteLeastUsedEntry() {
|
protected void deleteLeastUsedEntry() {
|
||||||
|
poolLock.lock();
|
||||||
try {
|
try {
|
||||||
poolLock.lock();
|
|
||||||
|
|
||||||
//@@@ with get() instead of remove, we could
|
|
||||||
//@@@ leave the removing to deleteEntry()
|
|
||||||
BasicPoolEntry entry = freeConnections.remove();
|
BasicPoolEntry entry = freeConnections.remove();
|
||||||
|
|
||||||
if (entry != null) {
|
if (entry != null) {
|
||||||
|
|
|
@ -289,7 +289,7 @@ public class ThreadSafeClientConnManager implements ClientConnectionManager {
|
||||||
|
|
||||||
public void closeIdleConnections(long idleTimeout, TimeUnit tunit) {
|
public void closeIdleConnections(long idleTimeout, TimeUnit tunit) {
|
||||||
if (log.isDebugEnabled()) {
|
if (log.isDebugEnabled()) {
|
||||||
log.debug("Closing connections idle for " + idleTimeout + " " + tunit);
|
log.debug("Closing connections idle longer than " + idleTimeout + " " + tunit);
|
||||||
}
|
}
|
||||||
pool.closeIdleConnections(idleTimeout, tunit);
|
pool.closeIdleConnections(idleTimeout, tunit);
|
||||||
}
|
}
|
||||||
|
|
|
@ -54,6 +54,7 @@ import org.apache.http.localserver.BasicServerTestBase;
|
||||||
import org.apache.http.localserver.LocalTestServer;
|
import org.apache.http.localserver.LocalTestServer;
|
||||||
import org.junit.Assert;
|
import org.junit.Assert;
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
|
import org.junit.Ignore;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -178,7 +179,7 @@ public class TestSSLSocketFactory extends BasicServerTestBase {
|
||||||
httpclient.execute(target, httpget);
|
httpclient.execute(target, httpget);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test @Ignore
|
||||||
public void testSSLTrustVerificationOverride() throws Exception {
|
public void testSSLTrustVerificationOverride() throws Exception {
|
||||||
// Use default SSL context
|
// Use default SSL context
|
||||||
SSLContext defaultsslcontext = SSLContext.getInstance("TLS");
|
SSLContext defaultsslcontext = SSLContext.getInstance("TLS");
|
||||||
|
|
|
@ -82,7 +82,7 @@ public class TestIdleConnectionEviction extends ServerTestBase {
|
||||||
HttpGet httpget = new HttpGet("/random/1024");
|
HttpGet httpget = new HttpGet("/random/1024");
|
||||||
WorkerThread[] workers = new WorkerThread[5];
|
WorkerThread[] workers = new WorkerThread[5];
|
||||||
for (int i = 0; i < workers.length; i++) {
|
for (int i = 0; i < workers.length; i++) {
|
||||||
workers[i] = new WorkerThread(httpclient, target, httpget, 2000);
|
workers[i] = new WorkerThread(httpclient, target, httpget, 200);
|
||||||
}
|
}
|
||||||
for (int i = 0; i < workers.length; i++) {
|
for (int i = 0; i < workers.length; i++) {
|
||||||
workers[i].start();
|
workers[i].start();
|
||||||
|
@ -132,6 +132,7 @@ public class TestIdleConnectionEviction extends ServerTestBase {
|
||||||
if (entity != null) {
|
if (entity != null) {
|
||||||
entity.consumeContent();
|
entity.consumeContent();
|
||||||
}
|
}
|
||||||
|
Thread.sleep(10);
|
||||||
}
|
}
|
||||||
} catch (Exception ex) {
|
} catch (Exception ex) {
|
||||||
this.ex = ex;
|
this.ex = ex;
|
||||||
|
|
Loading…
Reference in New Issue