You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@jclouds.apache.org by ga...@apache.org on 2016/06/22 01:13:22 UTC

jclouds-labs git commit: JCLOUDS-1005: Retry on 500 and 503 errors

Repository: jclouds-labs
Updated Branches:
  refs/heads/master 88ef0a221 -> d812c9d83


JCLOUDS-1005: Retry on 500 and 503 errors

This requires rewriting the URL for b2_upload_file and b2_upload_part
requests.


Project: http://git-wip-us.apache.org/repos/asf/jclouds-labs/repo
Commit: http://git-wip-us.apache.org/repos/asf/jclouds-labs/commit/d812c9d8
Tree: http://git-wip-us.apache.org/repos/asf/jclouds-labs/tree/d812c9d8
Diff: http://git-wip-us.apache.org/repos/asf/jclouds-labs/diff/d812c9d8

Branch: refs/heads/master
Commit: d812c9d833a82dd74c8631d4bf68663a6fd2a897
Parents: 88ef0a2
Author: Andrew Gaul <ga...@apache.org>
Authored: Tue Jun 14 21:35:19 2016 -0700
Committer: Andrew Gaul <ga...@apache.org>
Committed: Tue Jun 21 18:12:36 2016 -0700

----------------------------------------------------------------------
 .../main/java/org/jclouds/b2/B2ApiMetadata.java |  2 +
 .../org/jclouds/b2/config/B2HttpApiModule.java  |  7 ++
 .../org/jclouds/b2/filters/B2RetryHandler.java  | 90 ++++++++++++++++++++
 3 files changed, 99 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/d812c9d8/b2/src/main/java/org/jclouds/b2/B2ApiMetadata.java
----------------------------------------------------------------------
diff --git a/b2/src/main/java/org/jclouds/b2/B2ApiMetadata.java b/b2/src/main/java/org/jclouds/b2/B2ApiMetadata.java
index ef2e715..b5aecaa 100644
--- a/b2/src/main/java/org/jclouds/b2/B2ApiMetadata.java
+++ b/b2/src/main/java/org/jclouds/b2/B2ApiMetadata.java
@@ -48,6 +48,8 @@ public final class B2ApiMetadata extends BaseHttpApiMetadata {
    public static Properties defaultProperties() {
       Properties properties = BaseHttpApiMetadata.defaultProperties();
       properties.setProperty(Constants.PROPERTY_SESSION_INTERVAL, String.valueOf(TimeUnit.HOURS.toSeconds(1)));
+      properties.setProperty(Constants.PROPERTY_IDEMPOTENT_METHODS, "DELETE,GET,HEAD,OPTIONS,POST,PUT");
+      properties.setProperty(Constants.PROPERTY_RETRY_DELAY_START, String.valueOf(TimeUnit.SECONDS.toMillis(1)));
       return properties;
    }
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/d812c9d8/b2/src/main/java/org/jclouds/b2/config/B2HttpApiModule.java
----------------------------------------------------------------------
diff --git a/b2/src/main/java/org/jclouds/b2/config/B2HttpApiModule.java b/b2/src/main/java/org/jclouds/b2/config/B2HttpApiModule.java
index 11d8624..a30f9a4 100644
--- a/b2/src/main/java/org/jclouds/b2/config/B2HttpApiModule.java
+++ b/b2/src/main/java/org/jclouds/b2/config/B2HttpApiModule.java
@@ -26,9 +26,11 @@ import org.jclouds.Constants;
 import org.jclouds.collect.Memoized;
 import org.jclouds.b2.B2Api;
 import org.jclouds.b2.domain.Authorization;
+import org.jclouds.b2.filters.B2RetryHandler;
 import org.jclouds.b2.filters.RequestAuthorization;
 import org.jclouds.b2.handlers.ParseB2ErrorFromJsonContent;
 import org.jclouds.http.HttpErrorHandler;
+import org.jclouds.http.HttpRetryHandler;
 import org.jclouds.http.annotation.ClientError;
 import org.jclouds.http.annotation.Redirection;
 import org.jclouds.http.annotation.ServerError;
@@ -57,6 +59,11 @@ public final class B2HttpApiModule extends HttpApiModule<B2Api> {
       bind(HttpErrorHandler.class).annotatedWith(ServerError.class).to(ParseB2ErrorFromJsonContent.class);
    }
 
+   @Override
+   protected void bindRetryHandlers() {
+      bind(HttpRetryHandler.class).annotatedWith(ServerError.class).to(B2RetryHandler.class);
+   }
+
    @Provides
    @Singleton
    static Supplier<Authorization> provideAuthorizationSupplier(final B2Api b2Api) {

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/d812c9d8/b2/src/main/java/org/jclouds/b2/filters/B2RetryHandler.java
----------------------------------------------------------------------
diff --git a/b2/src/main/java/org/jclouds/b2/filters/B2RetryHandler.java b/b2/src/main/java/org/jclouds/b2/filters/B2RetryHandler.java
new file mode 100644
index 0000000..e58d712
--- /dev/null
+++ b/b2/src/main/java/org/jclouds/b2/filters/B2RetryHandler.java
@@ -0,0 +1,90 @@
+/*
+ * 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.
+ */
+package org.jclouds.b2.filters;
+
+import static org.jclouds.http.HttpUtils.closeClientButKeepContentStream;
+import static org.jclouds.http.HttpUtils.releasePayload;
+
+import javax.annotation.Resource;
+import javax.inject.Inject;
+
+import org.jclouds.b2.B2Api;
+import org.jclouds.b2.domain.GetUploadPartResponse;
+import org.jclouds.b2.domain.UploadUrlResponse;
+import org.jclouds.http.HttpCommand;
+import org.jclouds.http.HttpException;
+import org.jclouds.http.HttpRequest;
+import org.jclouds.http.HttpRequestFilter;
+import org.jclouds.http.HttpResponse;
+import org.jclouds.http.handlers.BackoffLimitedRetryHandler;
+import org.jclouds.logging.Logger;
+
+import com.google.common.net.HttpHeaders;
+import com.google.inject.Singleton;
+
+@Singleton
+public final class B2RetryHandler extends BackoffLimitedRetryHandler implements HttpRequestFilter {
+   private final B2Api api;
+
+   @Resource
+   private Logger logger = Logger.NULL;
+
+   @Inject
+   B2RetryHandler(B2Api api) {
+      this.api = api;
+   }
+
+   @Override
+   public HttpRequest filter(HttpRequest request) throws HttpException {
+      HttpRequest.Builder<?> builder = request.toBuilder();
+
+      // B2 requires retrying on a different storage node for uploads
+      String path = request.getEndpoint().getPath();
+      if (path.startsWith("/b2api/v1/b2_upload_file")) {
+         String bucketId = path.split("/")[4];
+         UploadUrlResponse uploadUrl = api.getObjectApi().getUploadUrl(bucketId);
+         builder.endpoint(uploadUrl.uploadUrl())
+               .replaceHeader(HttpHeaders.AUTHORIZATION, uploadUrl.authorizationToken());
+      } else if (path.startsWith("/b2api/v1/b2_upload_part")) {
+         String fileId = path.split("/")[4];
+         GetUploadPartResponse uploadUrl = api.getMultipartApi().getUploadPartUrl(fileId);
+         builder.endpoint(uploadUrl.uploadUrl())
+               .replaceHeader(HttpHeaders.AUTHORIZATION, uploadUrl.authorizationToken());
+      }
+
+      return builder.build();
+   }
+
+   @Override
+   public boolean shouldRetryRequest(HttpCommand command, HttpResponse response) {
+      boolean retry = false;
+      try {
+         byte[] data = closeClientButKeepContentStream(response);
+         switch (response.getStatusCode()) {
+         case 500:
+         case 503:
+            retry = super.shouldRetryRequest(command, response);
+            break;
+         default:
+            break;
+         }
+      } finally {
+         releasePayload(response);
+      }
+      return retry;
+   }
+}