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 2012/06/09 15:14:19 UTC

svn commit: r1348401 - in /httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client: DefaultHttpRequestRetryHandler.java exec/HttpRequestWrapper.java exec/MainRequestExecutor.java exec/RetryFacade.java

Author: olegk
Date: Sat Jun  9 13:14:19 2012
New Revision: 1348401

URL: http://svn.apache.org/viewvc?rev=1348401&view=rev
Log:
Added request execution retrial facade

Added:
    httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/RetryFacade.java   (with props)
Modified:
    httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/DefaultHttpRequestRetryHandler.java
    httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/HttpRequestWrapper.java
    httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/MainRequestExecutor.java

Modified: httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/DefaultHttpRequestRetryHandler.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/DefaultHttpRequestRetryHandler.java?rev=1348401&r1=1348400&r2=1348401&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/DefaultHttpRequestRetryHandler.java (original)
+++ httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/DefaultHttpRequestRetryHandler.java Sat Jun  9 13:14:19 2012
@@ -39,14 +39,13 @@ import org.apache.http.annotation.Immuta
 import org.apache.http.HttpEntityEnclosingRequest;
 import org.apache.http.HttpRequest;
 import org.apache.http.client.HttpRequestRetryHandler;
+import org.apache.http.client.methods.HttpUriRequest;
 import org.apache.http.protocol.HttpContext;
 import org.apache.http.protocol.ExecutionContext;
-import org.apache.http.client.methods.HttpUriRequest;
 
 /**
  * The default {@link HttpRequestRetryHandler} used by request executors.
  *
- *
  * @since 4.0
  */
 @Immutable
@@ -157,6 +156,8 @@ public class DefaultHttpRequestRetryHand
 
     /**
      * @since 4.2
+     * 
+     * @deprecated (4.3)
      */
     protected boolean requestIsAborted(final HttpRequest request) {
         HttpRequest req = request;

Modified: httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/HttpRequestWrapper.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/HttpRequestWrapper.java?rev=1348401&r1=1348400&r2=1348401&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/HttpRequestWrapper.java (original)
+++ httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/HttpRequestWrapper.java Sat Jun  9 13:14:19 2012
@@ -27,6 +27,9 @@
 
 package org.apache.http.impl.client.exec;
 
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
 import java.net.URI;
 import java.net.URISyntaxException;
 
@@ -41,6 +44,7 @@ import org.apache.http.ProtocolException
 import org.apache.http.ProtocolVersion;
 import org.apache.http.RequestLine;
 import org.apache.http.client.methods.HttpUriRequest;
+import org.apache.http.entity.HttpEntityWrapper;
 import org.apache.http.message.AbstractHttpMessage;
 import org.apache.http.message.BasicRequestLine;
 import org.apache.http.params.HttpProtocolParams;
@@ -137,6 +141,7 @@ public class HttpRequestWrapper extends 
         implements HttpEntityEnclosingRequest {
 
         private HttpEntity entity;
+        private boolean consumed;
 
         public HttpEntityEnclosingRequestWrapper(
                 final ProtocolVersion version,
@@ -153,7 +158,7 @@ public class HttpRequestWrapper extends 
         }
 
         public void setEntity(final HttpEntity entity) {
-            this.entity = entity;
+            this.entity = entity != null ? new EntityWrapper(entity) : null;
         }
 
         public boolean expectContinue() {
@@ -163,13 +168,34 @@ public class HttpRequestWrapper extends 
 
         @Override
         public boolean isRepeatable() {
-            if (this.entity != null) {
-                return this.entity.isRepeatable();
-            } else {
-                return true;
-            }
+            return this.entity == null || this.entity.isRepeatable() || !this.consumed;
         }
 
+        class EntityWrapper extends HttpEntityWrapper {
+
+            EntityWrapper(final HttpEntity entity) {
+                super(entity);
+            }
+
+            @Deprecated
+            @Override
+            public void consumeContent() throws IOException {
+                consumed = true;
+                super.consumeContent();
+            }
+
+            @Override
+            public InputStream getContent() throws IOException {
+                return super.getContent();
+            }
+
+            @Override
+            public void writeTo(final OutputStream outstream) throws IOException {
+                consumed = true;
+                super.writeTo(outstream);
+            }
+        }
+        
     }
 
     public static HttpRequestWrapper wrap(final HttpRequest request) throws ProtocolException {

Modified: httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/MainRequestExecutor.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/MainRequestExecutor.java?rev=1348401&r1=1348400&r2=1348401&view=diff
==============================================================================
--- httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/MainRequestExecutor.java (original)
+++ httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/MainRequestExecutor.java Sat Jun  9 13:14:19 2012
@@ -221,6 +221,8 @@ public class MainRequestExecutor impleme
         HttpHost target = route.getTargetHost();
         HttpHost proxy = route.getProxyHost();
 
+        HttpRequest original = request.getOriginal();
+        
         // Save original request headers
         Header[] origheaders = request.getAllHeaders();
 
@@ -257,7 +259,7 @@ public class MainRequestExecutor impleme
                 if (managedConn == null) {
                     ClientConnectionRequest connRequest = connManager.requestConnection(
                             route, userToken);
-                    if (request instanceof AbortableHttpRequest) {
+                    if (original instanceof AbortableHttpRequest) {
                         ((AbortableHttpRequest) request).setConnectionRequest(connRequest);
                     }
 
@@ -282,11 +284,12 @@ public class MainRequestExecutor impleme
                     }
                 }
 
-                if (request instanceof AbortableHttpRequest) {
+                if (original instanceof AbortableHttpRequest) {
                     ((AbortableHttpRequest) request).setReleaseTrigger(managedConn);
                 }
 
                 if (!managedConn.isOpen()) {
+                    this.log.debug("Opening connection " + route);
                     managedConn.open(route, context, params);
                 } else {
                     managedConn.setSocketTimeout(HttpConnectionParams.getSoTimeout(params));
@@ -310,6 +313,10 @@ public class MainRequestExecutor impleme
                             new BasicScheme(), new UsernamePasswordCredentials(userinfo));
                 }
 
+                if (this.log.isDebugEnabled()) {
+                    this.log.debug("Executing request " + request.getRequestLine());
+                }
+                
                 // Run request protocol interceptors
                 requestExec.preProcess(request, httpProcessor, context);
 

Added: httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/RetryFacade.java
URL: http://svn.apache.org/viewvc/httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/RetryFacade.java?rev=1348401&view=auto
==============================================================================
--- httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/RetryFacade.java (added)
+++ httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/RetryFacade.java Sat Jun  9 13:14:19 2012
@@ -0,0 +1,103 @@
+/*
+ * ====================================================================
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ * ====================================================================
+ *
+ * This software consists of voluntary contributions made by many
+ * individuals on behalf of the Apache Software Foundation.  For more
+ * information on the Apache Software Foundation, please see
+ * <http://www.apache.org/>.
+ *
+ */
+
+package org.apache.http.impl.client.exec;
+
+import java.io.IOException;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.http.HttpException;
+import org.apache.http.HttpRequest;
+import org.apache.http.HttpResponse;
+import org.apache.http.annotation.NotThreadSafe;
+import org.apache.http.client.HttpRequestRetryHandler;
+import org.apache.http.client.NonRepeatableRequestException;
+import org.apache.http.client.methods.HttpUriRequest;
+import org.apache.http.conn.routing.HttpRoute;
+import org.apache.http.protocol.HttpContext;
+
+/**
+ * @since 4.3
+ */
+@NotThreadSafe // e.g. managedConn
+public class RetryFacade implements HttpClientRequestExecutor {
+    
+    private final Log log = LogFactory.getLog(getClass());
+
+    private final HttpClientRequestExecutor requestExecutor;
+    private final HttpRequestRetryHandler retryHandler;
+
+    public RetryFacade(
+            final HttpClientRequestExecutor requestExecutor,
+            final HttpRequestRetryHandler retryHandler) {
+        if (requestExecutor == null) {
+            throw new IllegalArgumentException("HTTP request executor may not be null");
+        }
+        if (retryHandler == null) {
+            throw new IllegalArgumentException("HTTP request retry handler may not be null");
+        }
+        this.requestExecutor = requestExecutor;
+        this.retryHandler = retryHandler;
+    }
+
+    public HttpResponse execute(
+            final HttpRoute route, 
+            final HttpRequestWrapper request, 
+            final HttpContext context) throws IOException, HttpException {
+        for (int execCount = 0;; execCount++) {
+            try {
+                this.requestExecutor.execute(route, request, context);
+            } catch (IOException ex) {
+                HttpRequest original = request.getOriginal();
+                if (original instanceof HttpUriRequest && ((HttpUriRequest) original).isAborted()) {
+                    this.log.debug("Request has been aborted");
+                    throw ex;
+                }
+                if (retryHandler.retryRequest(ex, execCount, context)) {
+                    if (this.log.isInfoEnabled()) {
+                        this.log.info("I/O exception ("+ ex.getClass().getName() +
+                                ") caught when processing request: "
+                                + ex.getMessage());
+                    }
+                    if (this.log.isDebugEnabled()) {
+                        this.log.debug(ex.getMessage(), ex);
+                    }
+                    if (!request.isRepeatable()) {
+                        this.log.debug("Cannot retry non-repeatable request");
+                        throw new NonRepeatableRequestException("Cannot retry request " +
+                                "with a non-repeatable request entity", ex);
+                    }
+                    this.log.info("Retrying request");
+                } else {
+                    throw ex;
+                }
+            }
+        }
+    }
+
+}
\ No newline at end of file

Propchange: httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/RetryFacade.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/RetryFacade.java
------------------------------------------------------------------------------
    svn:keywords = Date Revision

Propchange: httpcomponents/httpclient/branches/decorator-refactoring/httpclient/src/main/java/org/apache/http/impl/client/exec/RetryFacade.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain