You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@hc.apache.org by ol...@apache.org on 2015/06/05 11:17:41 UTC
svn commit: r1683684 - in
/httpcomponents/httpclient/branches/4.5.x/httpclient/src:
main/java/org/apache/http/conn/ main/java/org/apache/http/impl/execchain/
test/java/org/apache/http/impl/execchain/
Author: olegk
Date: Fri Jun 5 09:17:41 2015
New Revision: 1683684
URL: http://svn.apache.org/r1683684
Log:
HTTPCLIENT-1655: HttpClient sends RST instead of FIN ACK sequence when using non-persistant connections
Modified:
httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/conn/ConnectionReleaseTrigger.java
httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ConnectionHolder.java
httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/HttpResponseProxy.java
httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ResponseEntityProxy.java
httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMainClientExec.java
httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMinimalClientExec.java
httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestResponseEntityWrapper.java
Modified: httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/conn/ConnectionReleaseTrigger.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/conn/ConnectionReleaseTrigger.java?rev=1683684&r1=1683683&r2=1683684&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/conn/ConnectionReleaseTrigger.java (original)
+++ httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/conn/ConnectionReleaseTrigger.java Fri Jun 5 09:17:41 2015
@@ -31,8 +31,7 @@ import java.io.IOException;
/**
* Interface for releasing a connection. This can be implemented by various
* "trigger" objects which are associated with a connection, for example
- * a {@link EofSensorInputStream stream} or an {@link BasicManagedEntity entity}
- * or the {@link ManagedClientConnection connection} itself.
+ * a {@link EofSensorInputStream} or the {@link ManagedHttpClientConnection} itself.
* <p>
* The methods in this interface can safely be called multiple times.
* The first invocation releases the connection, subsequent calls
Modified: httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ConnectionHolder.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ConnectionHolder.java?rev=1683684&r1=1683683&r2=1683684&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ConnectionHolder.java (original)
+++ httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ConnectionHolder.java Fri Jun 5 09:17:41 2015
@@ -30,6 +30,7 @@ package org.apache.http.impl.execchain;
import java.io.Closeable;
import java.io.IOException;
import java.util.concurrent.TimeUnit;
+import java.util.concurrent.atomic.AtomicBoolean;
import org.apache.commons.logging.Log;
import org.apache.http.HttpClientConnection;
@@ -50,13 +51,12 @@ class ConnectionHolder implements Connec
private final HttpClientConnectionManager manager;
private final HttpClientConnection managedConn;
+ private final AtomicBoolean released;
private volatile boolean reusable;
private volatile Object state;
private volatile long validDuration;
private volatile TimeUnit tunit;
- private volatile boolean released;
-
public ConnectionHolder(
final Log log,
final HttpClientConnectionManager manager,
@@ -65,6 +65,7 @@ class ConnectionHolder implements Connec
this.log = log;
this.manager = manager;
this.managedConn = managedConn;
+ this.released = new AtomicBoolean(false);
}
public boolean isReusable() {
@@ -90,19 +91,40 @@ class ConnectionHolder implements Connec
}
}
+ private void releaseConnection(final boolean reusable) {
+ if (this.released.compareAndSet(false, true)) {
+ synchronized (this.managedConn) {
+ if (reusable) {
+ this.manager.releaseConnection(this.managedConn,
+ this.state, this.validDuration, this.tunit);
+ } else {
+ try {
+ this.managedConn.close();
+ log.debug("Connection discarded");
+ } catch (final IOException ex) {
+ if (this.log.isDebugEnabled()) {
+ this.log.debug(ex.getMessage(), ex);
+ }
+ } finally {
+ this.manager.releaseConnection(
+ this.managedConn, null, 0, TimeUnit.MILLISECONDS);
+ }
+ }
+ }
+ }
+ }
+
@Override
public void releaseConnection() {
- synchronized (this.managedConn) {
- if (this.released) {
- return;
- }
- this.released = true;
- if (this.reusable) {
- this.manager.releaseConnection(this.managedConn,
- this.state, this.validDuration, this.tunit);
- } else {
+ releaseConnection(this.reusable);
+ }
+
+ @Override
+ public void abortConnection() {
+ if (this.released.compareAndSet(false, true)) {
+ synchronized (this.managedConn) {
try {
- this.managedConn.close();
+ this.managedConn.shutdown();
log.debug("Connection discarded");
} catch (final IOException ex) {
if (this.log.isDebugEnabled()) {
@@ -117,41 +139,20 @@ class ConnectionHolder implements Connec
}
@Override
- public void abortConnection() {
- synchronized (this.managedConn) {
- if (this.released) {
- return;
- }
- this.released = true;
- try {
- this.managedConn.shutdown();
- log.debug("Connection discarded");
- } catch (final IOException ex) {
- if (this.log.isDebugEnabled()) {
- this.log.debug(ex.getMessage(), ex);
- }
- } finally {
- this.manager.releaseConnection(
- this.managedConn, null, 0, TimeUnit.MILLISECONDS);
- }
- }
- }
-
- @Override
public boolean cancel() {
- final boolean alreadyReleased = this.released;
+ final boolean alreadyReleased = this.released.get();
log.debug("Cancelling request execution");
abortConnection();
return !alreadyReleased;
}
public boolean isReleased() {
- return this.released;
+ return this.released.get();
}
@Override
public void close() throws IOException {
- abortConnection();
+ releaseConnection(false);
}
}
Modified: httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/HttpResponseProxy.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/HttpResponseProxy.java?rev=1683684&r1=1683683&r2=1683684&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/HttpResponseProxy.java (original)
+++ httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/HttpResponseProxy.java Fri Jun 5 09:17:41 2015
@@ -61,7 +61,7 @@ class HttpResponseProxy implements Close
@Override
public void close() throws IOException {
if (this.connHolder != null) {
- this.connHolder.abortConnection();
+ this.connHolder.close();
}
}
Modified: httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ResponseEntityProxy.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ResponseEntityProxy.java?rev=1683684&r1=1683683&r2=1683684&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ResponseEntityProxy.java (original)
+++ httpcomponents/httpclient/branches/4.5.x/httpclient/src/main/java/org/apache/http/impl/execchain/ResponseEntityProxy.java Fri Jun 5 09:17:41 2015
@@ -61,7 +61,13 @@ class ResponseEntityProxy extends HttpEn
this.connHolder = connHolder;
}
- private void cleanup() {
+ private void cleanup() throws IOException {
+ if (this.connHolder != null) {
+ this.connHolder.close();
+ }
+ }
+
+ private void abortConnection() throws IOException {
if (this.connHolder != null) {
this.connHolder.abortConnection();
}
@@ -69,13 +75,7 @@ class ResponseEntityProxy extends HttpEn
public void releaseConnection() throws IOException {
if (this.connHolder != null) {
- try {
- if (this.connHolder.isReusable()) {
- this.connHolder.releaseConnection();
- }
- } finally {
- cleanup();
- }
+ this.connHolder.releaseConnection();
}
}
@@ -100,6 +100,12 @@ class ResponseEntityProxy extends HttpEn
try {
this.wrappedEntity.writeTo(outstream);
releaseConnection();
+ } catch (IOException ex) {
+ abortConnection();
+ throw ex;
+ } catch (RuntimeException ex) {
+ abortConnection();
+ throw ex;
} finally {
cleanup();
}
@@ -112,6 +118,12 @@ class ResponseEntityProxy extends HttpEn
// reading trailers after the response body:
wrapped.close();
releaseConnection();
+ } catch (IOException ex) {
+ abortConnection();
+ throw ex;
+ } catch (RuntimeException ex) {
+ abortConnection();
+ throw ex;
} finally {
cleanup();
}
@@ -132,6 +144,12 @@ class ResponseEntityProxy extends HttpEn
throw ex;
}
}
+ } catch (IOException ex) {
+ abortConnection();
+ throw ex;
+ } catch (RuntimeException ex) {
+ abortConnection();
+ throw ex;
} finally {
cleanup();
}
Modified: httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMainClientExec.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMainClientExec.java?rev=1683684&r1=1683683&r2=1683684&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMainClientExec.java (original)
+++ httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMainClientExec.java Fri Jun 5 09:17:41 2015
@@ -305,7 +305,7 @@ public class TestMainClientExec {
Mockito.verify(connManager, Mockito.times(1)).releaseConnection(
managedConn, null, 0, TimeUnit.MILLISECONDS);
- Mockito.verify(managedConn, Mockito.times(1)).shutdown();
+ Mockito.verify(managedConn, Mockito.times(1)).close();
}
@Test
Modified: httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMinimalClientExec.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMinimalClientExec.java?rev=1683684&r1=1683683&r2=1683684&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMinimalClientExec.java (original)
+++ httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestMinimalClientExec.java Fri Jun 5 09:17:41 2015
@@ -202,7 +202,7 @@ public class TestMinimalClientExec {
Mockito.verify(connManager, Mockito.times(1)).releaseConnection(
managedConn, null, 0, TimeUnit.MILLISECONDS);
- Mockito.verify(managedConn, Mockito.times(1)).shutdown();
+ Mockito.verify(managedConn, Mockito.times(1)).close();
}
@Test
Modified: httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestResponseEntityWrapper.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestResponseEntityWrapper.java?rev=1683684&r1=1683683&r2=1683684&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestResponseEntityWrapper.java (original)
+++ httpcomponents/httpclient/branches/4.5.x/httpclient/src/test/java/org/apache/http/impl/execchain/TestResponseEntityWrapper.java Fri Jun 5 09:17:41 2015
@@ -85,7 +85,7 @@ public class TestResponseEntityWrapper {
Mockito.when(connHolder.isReleased()).thenReturn(true);
Mockito.doThrow(new SocketException()).when(instream).close();
EntityUtils.consume(wrapper);
- Mockito.verify(connHolder).abortConnection();
+ Mockito.verify(connHolder).close();
}
@Test