Repository: jclouds-labs Updated Branches: refs/heads/master 2e3874301 -> a1684e2d8
Added rate limit module Project: http://git-wip-us.apache.org/repos/asf/jclouds-labs/repo Commit: http://git-wip-us.apache.org/repos/asf/jclouds-labs/commit/a1684e2d Tree: http://git-wip-us.apache.org/repos/asf/jclouds-labs/tree/a1684e2d Diff: http://git-wip-us.apache.org/repos/asf/jclouds-labs/diff/a1684e2d Branch: refs/heads/master Commit: a1684e2d8e3cb5e790decfef25c610d4c418fedd Parents: 2e38743 Author: Ignasi Barrera <[email protected]> Authored: Wed Oct 19 16:50:50 2016 +0200 Committer: Ignasi Barrera <[email protected]> Committed: Wed Oct 19 16:50:50 2016 +0200 ---------------------------------------------------------------------- .../arm/AzureComputeProviderMetadata.java | 22 +++++---- .../arm/config/AzureComputeRateLimitModule.java | 30 ++++++++++++ .../AzureComputeRateLimitExceededException.java | 51 ++++++++++++++++++++ .../arm/handlers/AzureComputeErrorHandler.java | 6 ++- .../handlers/AzureRateLimitRetryHandler.java | 39 +++++++++++++++ 5 files changed, 137 insertions(+), 11 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/a1684e2d/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeProviderMetadata.java ---------------------------------------------------------------------- diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeProviderMetadata.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeProviderMetadata.java index beac925..dd516ef 100644 --- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeProviderMetadata.java +++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeProviderMetadata.java @@ -17,6 +17,7 @@ package org.jclouds.azurecompute.arm; +import static org.jclouds.Constants.PROPERTY_MAX_RATE_LIMIT_WAIT; import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.API_VERSION_PREFIX; import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.DEFAULT_DATADISKSIZE; import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.DEFAULT_SUBNET_ADDRESS_PREFIX; @@ -30,6 +31,8 @@ import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.TCP_RUL import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.TCP_RULE_REGEXP; import static org.jclouds.compute.config.ComputeServiceProperties.IMAGE_AUTHENTICATE_SUDO; import static org.jclouds.compute.config.ComputeServiceProperties.IMAGE_LOGIN_USER; +import static org.jclouds.compute.config.ComputeServiceProperties.POLL_INITIAL_PERIOD; +import static org.jclouds.compute.config.ComputeServiceProperties.POLL_MAX_PERIOD; import static org.jclouds.compute.config.ComputeServiceProperties.RESOURCENAME_DELIMITER; import static org.jclouds.compute.config.ComputeServiceProperties.RESOURCENAME_PREFIX; import static org.jclouds.compute.config.ComputeServiceProperties.TEMPLATE; @@ -56,7 +59,6 @@ import org.jclouds.azurecompute.arm.features.SubnetApi; import org.jclouds.azurecompute.arm.features.VMSizeApi; import org.jclouds.azurecompute.arm.features.VirtualMachineApi; import org.jclouds.azurecompute.arm.features.VirtualNetworkApi; -import org.jclouds.compute.config.ComputeServiceProperties; import org.jclouds.providers.ProviderMetadata; import org.jclouds.providers.internal.BaseProviderMetadata; @@ -80,20 +82,22 @@ public class AzureComputeProviderMetadata extends BaseProviderMetadata { public static Properties defaultProperties() { final Properties properties = AzureManagementApiMetadata.defaultProperties(); - properties.put(ComputeServiceProperties.POLL_INITIAL_PERIOD, 1000); - properties.put(ComputeServiceProperties.POLL_MAX_PERIOD, 10000); - properties.setProperty(OPERATION_TIMEOUT, "46000000"); - properties.setProperty(OPERATION_POLL_INITIAL_PERIOD, "5"); - properties.setProperty(OPERATION_POLL_MAX_PERIOD, "15"); - properties.setProperty(TCP_RULE_FORMAT, "tcp_%s-%s"); - properties.setProperty(TCP_RULE_REGEXP, "tcp_\\d{1,5}-\\d{1,5}"); + properties.put(POLL_INITIAL_PERIOD, 1000); + properties.put(POLL_MAX_PERIOD, 10000); + properties.put(OPERATION_TIMEOUT, 46000000); + properties.put(OPERATION_POLL_INITIAL_PERIOD, 5); + properties.put(OPERATION_POLL_MAX_PERIOD, 15); + // Default max wait in rate limit: 5m30s + properties.put(PROPERTY_MAX_RATE_LIMIT_WAIT, 330000); + properties.put(TCP_RULE_FORMAT, "tcp_%s-%s"); + properties.put(TCP_RULE_REGEXP, "tcp_\\d{1,5}-\\d{1,5}"); properties.put(RESOURCE, "https://management.azure.com/"); properties.put(CREDENTIAL_TYPE, CLIENT_CREDENTIALS_SECRET.toString()); properties.put(DEFAULT_VNET_ADDRESS_SPACE_PREFIX, "10.0.0.0/16"); properties.put(DEFAULT_SUBNET_ADDRESS_PREFIX, "10.0.0.0/24"); properties.put(RESOURCENAME_PREFIX, "jclouds"); properties.put(RESOURCENAME_DELIMITER, "-"); - properties.put(DEFAULT_DATADISKSIZE, "100"); + properties.put(DEFAULT_DATADISKSIZE, 100); properties.put(IMAGE_PUBLISHERS, "Canonical,RedHat"); // Default credentials for all images properties.put(IMAGE_LOGIN_USER, "jclouds:Password12345!"); http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/a1684e2d/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeRateLimitModule.java ---------------------------------------------------------------------- diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeRateLimitModule.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeRateLimitModule.java new file mode 100644 index 0000000..3038b86 --- /dev/null +++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeRateLimitModule.java @@ -0,0 +1,30 @@ +/* + * 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.azurecompute.arm.config; + +import org.jclouds.azurecompute.arm.handlers.AzureRateLimitRetryHandler; +import org.jclouds.http.HttpRetryHandler; +import org.jclouds.http.annotation.ClientError; + +import com.google.inject.AbstractModule; + +public class AzureComputeRateLimitModule extends AbstractModule { + @Override + protected void configure() { + bind(HttpRetryHandler.class).annotatedWith(ClientError.class).to(AzureRateLimitRetryHandler.class); + } +} http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/a1684e2d/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/exceptions/AzureComputeRateLimitExceededException.java ---------------------------------------------------------------------- diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/exceptions/AzureComputeRateLimitExceededException.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/exceptions/AzureComputeRateLimitExceededException.java new file mode 100644 index 0000000..d8d478e --- /dev/null +++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/exceptions/AzureComputeRateLimitExceededException.java @@ -0,0 +1,51 @@ +/* + * 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.azurecompute.arm.exceptions; + +import org.jclouds.http.HttpResponse; +import org.jclouds.rest.RateLimitExceededException; + +import com.google.common.annotations.Beta; +import com.google.common.base.Predicate; +import com.google.common.collect.Multimap; +import com.google.common.collect.Multimaps; + +/** + * Provides detailed information for rate limit exceptions. + */ +@Beta +public class AzureComputeRateLimitExceededException extends RateLimitExceededException { + private static final long serialVersionUID = 1L; + private static final String RATE_LIMIT_HEADER_PREFIX = "x-ms-ratelimit-remaining-"; + + public AzureComputeRateLimitExceededException(HttpResponse response) { + super(response.getStatusLine() + "\n" + rateLimitHeaders(response)); + } + + public AzureComputeRateLimitExceededException(HttpResponse response, Throwable cause) { + super(response.getStatusLine() + "\n" + rateLimitHeaders(response), cause); + } + + private static Multimap<String, String> rateLimitHeaders(HttpResponse response) { + return Multimaps.filterKeys(response.getHeaders(), new Predicate<String>() { + @Override + public boolean apply(String input) { + return input.startsWith(RATE_LIMIT_HEADER_PREFIX); + } + }); + } +} http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/a1684e2d/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureComputeErrorHandler.java ---------------------------------------------------------------------- diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureComputeErrorHandler.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureComputeErrorHandler.java index 6532173..8492d51 100644 --- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureComputeErrorHandler.java +++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureComputeErrorHandler.java @@ -20,6 +20,7 @@ import java.io.IOException; import javax.inject.Singleton; +import org.jclouds.azurecompute.arm.exceptions.AzureComputeRateLimitExceededException; import org.jclouds.http.HttpCommand; import org.jclouds.http.HttpErrorHandler; import org.jclouds.http.HttpResponse; @@ -65,11 +66,12 @@ public class AzureComputeErrorHandler implements HttpErrorHandler { exception = new ResourceNotFoundException(message, exception); } break; - case 409: exception = new IllegalStateException(message, exception); break; - + case 429: + exception = new AzureComputeRateLimitExceededException(response, exception); + break; default: } } finally { http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/a1684e2d/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureRateLimitRetryHandler.java ---------------------------------------------------------------------- diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureRateLimitRetryHandler.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureRateLimitRetryHandler.java new file mode 100644 index 0000000..ee5f5e5 --- /dev/null +++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/handlers/AzureRateLimitRetryHandler.java @@ -0,0 +1,39 @@ +/* + * 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.azurecompute.arm.handlers; + +import javax.inject.Singleton; + +import org.jclouds.http.HttpCommand; +import org.jclouds.http.HttpResponse; +import org.jclouds.http.handlers.RateLimitRetryHandler; + +import com.google.common.annotations.Beta; +import com.google.common.base.Optional; +import com.google.common.net.HttpHeaders; + +@Beta +@Singleton +public class AzureRateLimitRetryHandler extends RateLimitRetryHandler { + + @Override + protected Optional<Long> millisToNextAvailableRequest(HttpCommand command, HttpResponse response) { + String secondsToNextAvailableRequest = response.getFirstHeaderOrNull(HttpHeaders.RETRY_AFTER); + return secondsToNextAvailableRequest != null ? Optional.of(Long.valueOf(secondsToNextAvailableRequest) * 1000) + : Optional.<Long> absent(); + } +}
