You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@jclouds.apache.org by na...@apache.org on 2016/10/05 10:29:28 UTC

jclouds-labs git commit: Make api versions configurable

Repository: jclouds-labs
Updated Branches:
  refs/heads/fix/AzureTemplateBuilderLiveTest 8d223b1ee -> 8d0cd4d85


Make api versions configurable


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

Branch: refs/heads/fix/AzureTemplateBuilderLiveTest
Commit: 8d0cd4d85eafc1e406b8d4678656694ebb3d87fd
Parents: 8d223b1
Author: Ignasi Barrera <na...@apache.org>
Authored: Wed Oct 5 12:29:10 2016 +0200
Committer: Ignasi Barrera <na...@apache.org>
Committed: Wed Oct 5 12:29:10 2016 +0200

----------------------------------------------------------------------
 .../azurecompute/arm/AzureComputeApi.java       |  14 +-
 .../arm/AzureComputeProviderMetadata.java       |  57 ++++++--
 .../arm/config/AzureComputeProperties.java      |   5 +-
 .../arm/features/DeploymentApi.java             |   5 +-
 .../azurecompute/arm/features/JobApi.java       |   7 +-
 .../azurecompute/arm/features/LocationApi.java  |   7 +-
 .../arm/features/NetworkInterfaceCardApi.java   |  31 +++--
 .../arm/features/NetworkSecurityGroupApi.java   |  46 +++----
 .../arm/features/NetworkSecurityRuleApi.java    |  38 +++---
 .../azurecompute/arm/features/OSImageApi.java   |   5 +-
 .../arm/features/PublicIPAddressApi.java        |  29 ++---
 .../arm/features/ResourceGroupApi.java          |  19 ++-
 .../arm/features/ResourceProviderApi.java       |  24 ++--
 .../arm/features/StorageAccountApi.java         |  35 +++--
 .../azurecompute/arm/features/SubnetApi.java    |  33 +++--
 .../azurecompute/arm/features/VMSizeApi.java    |  20 +--
 .../arm/features/VirtualMachineApi.java         |   9 +-
 .../arm/features/VirtualNetworkApi.java         |  35 +++--
 .../arm/filters/ApiVersionFilter.java           |  90 +++++++++++++
 .../arm/features/DeploymentApiLiveTest.java     |  45 +------
 .../NetworkSecurityGroupApiMockTest.java        |   2 -
 .../features/PublicIPAddressApiMockTest.java    |   3 +-
 .../features/ResourceProviderAPIMockTest.java   |   1 -
 .../arm/features/StorageAccountApiMockTest.java |  35 -----
 .../arm/features/SubnetApiMockTest.java         |  17 ++-
 .../arm/features/VirtualMachineApiLiveTest.java |   4 -
 .../arm/features/VirtualMachineApiMockTest.java |  18 +--
 .../arm/features/VirtualNetworkApiMockTest.java |   2 +-
 .../arm/filters/ApiVersionFilterTest.java       | 129 +++++++++++++++++++
 .../internal/BaseAzureComputeApiMockTest.java   |  12 +-
 30 files changed, 468 insertions(+), 309 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeApi.java
index 7706737..c0c0994 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/AzureComputeApi.java
@@ -16,27 +16,27 @@
  */
 package org.jclouds.azurecompute.arm;
 
+import java.io.Closeable;
+
+import javax.ws.rs.PathParam;
+
 import org.jclouds.azurecompute.arm.features.DeploymentApi;
 import org.jclouds.azurecompute.arm.features.JobApi;
 import org.jclouds.azurecompute.arm.features.LocationApi;
 import org.jclouds.azurecompute.arm.features.NetworkInterfaceCardApi;
+import org.jclouds.azurecompute.arm.features.NetworkSecurityGroupApi;
+import org.jclouds.azurecompute.arm.features.NetworkSecurityRuleApi;
 import org.jclouds.azurecompute.arm.features.OSImageApi;
 import org.jclouds.azurecompute.arm.features.PublicIPAddressApi;
 import org.jclouds.azurecompute.arm.features.ResourceGroupApi;
 import org.jclouds.azurecompute.arm.features.ResourceProviderApi;
 import org.jclouds.azurecompute.arm.features.StorageAccountApi;
 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.azurecompute.arm.features.VMSizeApi;
-import org.jclouds.azurecompute.arm.features.NetworkSecurityGroupApi;
-import org.jclouds.azurecompute.arm.features.NetworkSecurityRuleApi;
 import org.jclouds.rest.annotations.Delegate;
 
-import com.google.inject.Provides;
-import javax.ws.rs.PathParam;
-import java.io.Closeable;
-
 /**
  * The Azure Resource Manager API is a REST API for managing your services and deployments.
  * <p>

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/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 cf98a8d..9eeaac9 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,16 +17,7 @@
 package org.jclouds.azurecompute.arm;
 
 
-import java.net.URI;
-import java.util.Properties;
-
-import org.jclouds.azurecompute.arm.domain.Region;
-import org.jclouds.compute.config.ComputeServiceProperties;
-import org.jclouds.providers.ProviderMetadata;
-import org.jclouds.providers.internal.BaseProviderMetadata;
-
-import com.google.auto.service.AutoService;
-
+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;
 import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.DEFAULT_VNET_ADDRESS_SPACE_PREFIX;
@@ -35,6 +26,7 @@ import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.OPERATI
 import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.OPERATION_POLL_MAX_PERIOD;
 import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.OPERATION_TIMEOUT;
 import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.RESOURCE_GROUP_NAME;
+import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.STORAGE_API_VERSION;
 import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.TCP_RULE_FORMAT;
 import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.TCP_RULE_REGEXP;
 import static org.jclouds.compute.config.ComputeServiceProperties.TIMEOUT_NODE_TERMINATED;
@@ -42,6 +34,30 @@ import static org.jclouds.oauth.v2.config.CredentialType.CLIENT_CREDENTIALS_SECR
 import static org.jclouds.oauth.v2.config.OAuthProperties.CREDENTIAL_TYPE;
 import static org.jclouds.oauth.v2.config.OAuthProperties.RESOURCE;
 
+import java.net.URI;
+import java.util.Properties;
+
+import org.jclouds.azurecompute.arm.domain.Region;
+import org.jclouds.azurecompute.arm.features.DeploymentApi;
+import org.jclouds.azurecompute.arm.features.LocationApi;
+import org.jclouds.azurecompute.arm.features.NetworkInterfaceCardApi;
+import org.jclouds.azurecompute.arm.features.NetworkSecurityGroupApi;
+import org.jclouds.azurecompute.arm.features.NetworkSecurityRuleApi;
+import org.jclouds.azurecompute.arm.features.OSImageApi;
+import org.jclouds.azurecompute.arm.features.PublicIPAddressApi;
+import org.jclouds.azurecompute.arm.features.ResourceGroupApi;
+import org.jclouds.azurecompute.arm.features.ResourceProviderApi;
+import org.jclouds.azurecompute.arm.features.StorageAccountApi;
+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;
+
+import com.google.auto.service.AutoService;
+
 @AutoService(ProviderMetadata.class)
 public class AzureComputeProviderMetadata extends BaseProviderMetadata {
 
@@ -78,6 +94,27 @@ public class AzureComputeProviderMetadata extends BaseProviderMetadata {
       properties.put("jclouds.image.login-user", "jclouds:Password1!");
       properties.put("jclouds.image.authenticate-sudo", "true");      
       properties.put(TIMEOUT_NODE_TERMINATED, 60 * 10 * 1000);
+      // Api versions used in each API
+      properties.put(API_VERSION_PREFIX + DeploymentApi.class.getSimpleName(), "2016-02-01");
+      properties.put(API_VERSION_PREFIX + LocationApi.class.getSimpleName(), "2015-11-01");
+      properties.put(API_VERSION_PREFIX + NetworkInterfaceCardApi.class.getSimpleName(), "2015-06-15");
+      properties.put(API_VERSION_PREFIX + NetworkSecurityGroupApi.class.getSimpleName(), "2016-03-30");
+      properties.put(API_VERSION_PREFIX + NetworkSecurityRuleApi.class.getSimpleName(), "2016-03-30");
+      properties.put(API_VERSION_PREFIX + OSImageApi.class.getSimpleName(), "2015-06-15");
+      properties.put(API_VERSION_PREFIX + PublicIPAddressApi.class.getSimpleName(), "2015-06-15");
+      properties.put(API_VERSION_PREFIX + ResourceGroupApi.class.getSimpleName(), "2015-01-01");
+      properties.put(API_VERSION_PREFIX + ResourceProviderApi.class.getSimpleName(), "2015-01-01");
+      properties.put(API_VERSION_PREFIX + StorageAccountApi.class.getSimpleName(), STORAGE_API_VERSION);
+      properties.put(API_VERSION_PREFIX + SubnetApi.class.getSimpleName(), "2015-06-15");
+      properties.put(API_VERSION_PREFIX + VirtualNetworkApi.class.getSimpleName(), "2015-06-15");
+      properties.put(API_VERSION_PREFIX + VMSizeApi.class.getSimpleName(), "2015-06-15");
+      properties.put(API_VERSION_PREFIX + VirtualMachineApi.class.getSimpleName(), "2015-06-15");
+      properties.put(API_VERSION_PREFIX + "GetVirtualMachine", "2016-03-30");
+      properties.put(API_VERSION_PREFIX + "GetVirtualMachineInstance", "2016-03-30");
+      properties.put(API_VERSION_PREFIX + "CreateVirtualMachine", "2016-03-30");
+      properties.put(API_VERSION_PREFIX + "ListVirtualMachines", "2016-06-01");
+      properties.put(API_VERSION_PREFIX + "DeleteVirtualMachine", "2016-03-30");
+      
       return properties;
    }
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeProperties.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeProperties.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeProperties.java
index 968ba3f..8f945d9 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeProperties.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/config/AzureComputeProperties.java
@@ -17,7 +17,8 @@
 package org.jclouds.azurecompute.arm.config;
 
 /**
- * Configuration properties and constants used in Azure Resource Manager connections.
+ * Configuration properties and constants used in Azure Resource Manager
+ * connections.
  */
 public class AzureComputeProperties {
 
@@ -47,4 +48,6 @@ public class AzureComputeProperties {
 
    public static final String DEFAULT_DATADISKSIZE = "jclouds.azurecompute.arm.datadisksize";
 
+   public static final String API_VERSION_PREFIX = "jclouds.azurecompute.arm.apiversion.";
+
 }

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/DeploymentApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/DeploymentApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/DeploymentApi.java
index 33c929a..8d446a5 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/DeploymentApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/DeploymentApi.java
@@ -34,12 +34,12 @@ import org.jclouds.Fallbacks;
 import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
 import org.jclouds.Fallbacks.NullOnNotFoundOr404;
 import org.jclouds.azurecompute.arm.domain.Deployment;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.azurecompute.arm.functions.URIParser;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
 import org.jclouds.rest.annotations.Fallback;
 import org.jclouds.rest.annotations.Payload;
 import org.jclouds.rest.annotations.PayloadParam;
-import org.jclouds.rest.annotations.QueryParams;
 import org.jclouds.rest.annotations.RequestFilters;
 import org.jclouds.rest.annotations.ResponseParser;
 import org.jclouds.rest.annotations.SelectJson;
@@ -50,8 +50,7 @@ import org.jclouds.rest.annotations.SelectJson;
  * - get information about deployment
  */
 @Path("/resourcegroups/{resourcegroup}/providers/microsoft.resources/deployments")
-@QueryParams(keys = "api-version", values = "2016-02-01")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface DeploymentApi {
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/JobApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/JobApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/JobApi.java
index f2858d9..3c3bab9 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/JobApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/JobApi.java
@@ -18,19 +18,20 @@ package org.jclouds.azurecompute.arm.features;
 import java.io.Closeable;
 import java.net.URI;
 import java.util.List;
+
 import javax.ws.rs.Consumes;
-import javax.ws.rs.core.MediaType;
 import javax.ws.rs.GET;
+import javax.ws.rs.core.MediaType;
 
 import org.jclouds.Fallbacks;
 import org.jclouds.azurecompute.arm.domain.ResourceDefinition;
+import org.jclouds.azurecompute.arm.functions.ParseJobStatus;
+import org.jclouds.azurecompute.arm.functions.ParseJobStatus.JobStatus;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
 import org.jclouds.rest.annotations.EndpointParam;
 import org.jclouds.rest.annotations.Fallback;
 import org.jclouds.rest.annotations.RequestFilters;
 import org.jclouds.rest.annotations.ResponseParser;
-import org.jclouds.azurecompute.arm.functions.ParseJobStatus;
-import org.jclouds.azurecompute.arm.functions.ParseJobStatus.JobStatus;
 import org.jclouds.rest.annotations.SelectJson;
 
 /**

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/LocationApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/LocationApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/LocationApi.java
index 8f31d31..257293c 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/LocationApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/LocationApi.java
@@ -27,11 +27,11 @@ import javax.ws.rs.core.MediaType;
 
 import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
 import org.jclouds.azurecompute.arm.domain.Location;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
-import org.jclouds.rest.annotations.QueryParams;
+import org.jclouds.rest.annotations.Fallback;
 import org.jclouds.rest.annotations.RequestFilters;
 import org.jclouds.rest.annotations.SelectJson;
-import org.jclouds.rest.annotations.Fallback;
 
 /**
  * This Azure Resource Manager API provides all of the locations that are available for resource providers
@@ -40,8 +40,7 @@ import org.jclouds.rest.annotations.Fallback;
  * @see <a href="https://msdn.microsoft.com/en-US/library/azure/dn790540.aspx">docs</a>
  */
 @Path("/locations")
-@RequestFilters(OAuthFilter.class)
-@QueryParams(keys = "api-version", values = "2015-11-01")
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Produces(MediaType.APPLICATION_JSON)
 @Consumes(MediaType.APPLICATION_JSON)
 public interface LocationApi {

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkInterfaceCardApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkInterfaceCardApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkInterfaceCardApi.java
index 2f19996..c135e9e 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkInterfaceCardApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkInterfaceCardApi.java
@@ -16,38 +16,37 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
+import java.net.URI;
+import java.util.List;
+import java.util.Map;
+
+import javax.inject.Named;
+import javax.ws.rs.Consumes;
+import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.PUT;
+import javax.ws.rs.Path;
+import javax.ws.rs.PathParam;
+import javax.ws.rs.core.MediaType;
+
 import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
 import org.jclouds.Fallbacks.NullOnNotFoundOr404;
 import org.jclouds.azurecompute.arm.domain.NetworkInterfaceCard;
 import org.jclouds.azurecompute.arm.domain.NetworkInterfaceCardProperties;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.azurecompute.arm.functions.URIParser;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
 import org.jclouds.rest.annotations.Fallback;
 import org.jclouds.rest.annotations.MapBinder;
 import org.jclouds.rest.annotations.PayloadParam;
-import org.jclouds.rest.annotations.QueryParams;
 import org.jclouds.rest.annotations.RequestFilters;
 import org.jclouds.rest.annotations.ResponseParser;
 import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.binders.BindToJsonPayload;
 
-import javax.inject.Named;
-import javax.ws.rs.Consumes;
-import javax.ws.rs.DELETE;
-import javax.ws.rs.GET;
-import javax.ws.rs.PUT;
-import javax.ws.rs.Path;
-import javax.ws.rs.PathParam;
-import javax.ws.rs.core.MediaType;
-import java.util.List;
-import java.util.Map;
-import java.net.URI;
-
 @Path("/resourcegroups/{resourcegroup}/providers/Microsoft.Network/networkInterfaces")
-@QueryParams(keys = "api-version", values = "2015-06-15")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
-
 public interface NetworkInterfaceCardApi {
 
    @Named("networkinterfacecard:list")

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApi.java
index e6b310d..ba4c2cd 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApi.java
@@ -16,40 +16,38 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
+import java.net.URI;
+import java.util.List;
+import java.util.Map;
+
+import javax.inject.Named;
+import javax.ws.rs.Consumes;
+import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.PUT;
+import javax.ws.rs.Path;
+import javax.ws.rs.PathParam;
+import javax.ws.rs.Produces;
+import javax.ws.rs.core.MediaType;
+
 import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
 import org.jclouds.Fallbacks.NullOnNotFoundOr404;
 import org.jclouds.azurecompute.arm.domain.NetworkSecurityGroup;
 import org.jclouds.azurecompute.arm.domain.NetworkSecurityGroupProperties;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.azurecompute.arm.functions.URIParser;
 import org.jclouds.javax.annotation.Nullable;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
-
-import org.jclouds.rest.annotations.RequestFilters;
-import org.jclouds.rest.annotations.QueryParams;
-import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.annotations.Fallback;
+import org.jclouds.rest.annotations.MapBinder;
 import org.jclouds.rest.annotations.PayloadParam;
+import org.jclouds.rest.annotations.RequestFilters;
 import org.jclouds.rest.annotations.ResponseParser;
-import org.jclouds.rest.annotations.MapBinder;
+import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.binders.BindToJsonPayload;
 
-import javax.inject.Named;
-import javax.ws.rs.Produces;
-import javax.ws.rs.Path;
-import javax.ws.rs.Consumes;
-import javax.ws.rs.GET;
-import javax.ws.rs.DELETE;
-import javax.ws.rs.PUT;
-import javax.ws.rs.PathParam;
-import javax.ws.rs.core.MediaType;
-import java.net.URI;
-import java.util.List;
-import java.util.Map;
-
 @Path("/resourcegroups/{resourcegroup}/providers/Microsoft.Network/networkSecurityGroups")
-
-@QueryParams(keys = "api-version", values = "2016-03-30")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface NetworkSecurityGroupApi {
 
@@ -72,9 +70,8 @@ public interface NetworkSecurityGroupApi {
    @MapBinder(BindToJsonPayload.class)
    @Produces(MediaType.APPLICATION_JSON)
    NetworkSecurityGroup createOrUpdate(@PathParam("networksecuritygroupname") String nsgName,
-                                       @PayloadParam("location") String location,
-                                       @Nullable @PayloadParam("tags") Map<String, String> tags,
-                                       @PayloadParam("properties")NetworkSecurityGroupProperties properties);
+         @PayloadParam("location") String location, @Nullable @PayloadParam("tags") Map<String, String> tags,
+         @PayloadParam("properties") NetworkSecurityGroupProperties properties);
 
    @Named("networksecuritygroup:get")
    @Path("/{networksecuritygroupname}")
@@ -82,4 +79,3 @@ public interface NetworkSecurityGroupApi {
    @Fallback(NullOnNotFoundOr404.class)
    NetworkSecurityGroup get(@PathParam("networksecuritygroupname") String nsgName);
 }
-

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityRuleApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityRuleApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityRuleApi.java
index 2edd3df..8def4e3 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityRuleApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/NetworkSecurityRuleApi.java
@@ -16,38 +16,36 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
+import java.net.URI;
+import java.util.List;
+
+import javax.inject.Named;
+import javax.ws.rs.Consumes;
+import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.PUT;
+import javax.ws.rs.Path;
+import javax.ws.rs.PathParam;
+import javax.ws.rs.Produces;
+import javax.ws.rs.core.MediaType;
+
 import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
 import org.jclouds.Fallbacks.NullOnNotFoundOr404;
 import org.jclouds.azurecompute.arm.domain.NetworkSecurityRule;
 import org.jclouds.azurecompute.arm.domain.NetworkSecurityRuleProperties;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.azurecompute.arm.functions.URIParser;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
-
-import org.jclouds.rest.annotations.RequestFilters;
-import org.jclouds.rest.annotations.QueryParams;
-import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.annotations.Fallback;
+import org.jclouds.rest.annotations.MapBinder;
 import org.jclouds.rest.annotations.PayloadParam;
+import org.jclouds.rest.annotations.RequestFilters;
 import org.jclouds.rest.annotations.ResponseParser;
-import org.jclouds.rest.annotations.MapBinder;
+import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.binders.BindToJsonPayload;
 
-import javax.inject.Named;
-import javax.ws.rs.Produces;
-import javax.ws.rs.Path;
-import javax.ws.rs.Consumes;
-import javax.ws.rs.GET;
-import javax.ws.rs.DELETE;
-import javax.ws.rs.PUT;
-import javax.ws.rs.PathParam;
-import javax.ws.rs.core.MediaType;
-import java.util.List;
-import java.net.URI;
-
 @Path("/resourcegroups/{resourcegroup}/providers/Microsoft.Network/networkSecurityGroups/{networksecuritygroup}")
-
-@QueryParams(keys = "api-version", values = "2016-03-30")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface NetworkSecurityRuleApi {
    @Named("networksecurityrule:createOrUpdate")

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/OSImageApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/OSImageApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/OSImageApi.java
index 96dce6b..c8fb3f3 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/OSImageApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/OSImageApi.java
@@ -31,17 +31,16 @@ import org.jclouds.azurecompute.arm.domain.Offer;
 import org.jclouds.azurecompute.arm.domain.Publisher;
 import org.jclouds.azurecompute.arm.domain.SKU;
 import org.jclouds.azurecompute.arm.domain.Version;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
 import org.jclouds.rest.annotations.Fallback;
-import org.jclouds.rest.annotations.QueryParams;
 import org.jclouds.rest.annotations.RequestFilters;
 
 /**
  * The Azure Resource Management API includes operations for managing the OS images in your subscription.
  */
 @Path("/providers/Microsoft.Compute/locations/{location}")
-@RequestFilters(OAuthFilter.class)
-@QueryParams(keys = "api-version", values = "2015-06-15")
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(APPLICATION_JSON)
 public interface OSImageApi {
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApi.java
index 2e19fe2..2693753 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApi.java
@@ -16,37 +16,36 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
+import java.util.List;
+import java.util.Map;
+
+import javax.inject.Named;
+import javax.ws.rs.Consumes;
+import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.PUT;
+import javax.ws.rs.Path;
+import javax.ws.rs.PathParam;
+import javax.ws.rs.core.MediaType;
+
 import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
 import org.jclouds.Fallbacks.NullOnNotFoundOr404;
 import org.jclouds.azurecompute.arm.domain.PublicIPAddress;
 import org.jclouds.azurecompute.arm.domain.PublicIPAddressProperties;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.azurecompute.arm.functions.FalseOn204;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
 import org.jclouds.rest.annotations.Fallback;
 import org.jclouds.rest.annotations.MapBinder;
 import org.jclouds.rest.annotations.PayloadParam;
-import org.jclouds.rest.annotations.QueryParams;
 import org.jclouds.rest.annotations.RequestFilters;
 import org.jclouds.rest.annotations.ResponseParser;
 import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.binders.BindToJsonPayload;
 
-import javax.inject.Named;
-import javax.ws.rs.Consumes;
-import javax.ws.rs.DELETE;
-import javax.ws.rs.GET;
-import javax.ws.rs.PUT;
-import javax.ws.rs.Path;
-import javax.ws.rs.PathParam;
-import javax.ws.rs.core.MediaType;
-import java.util.List;
-import java.util.Map;
-
 @Path("/resourcegroups/{resourcegroup}/providers/Microsoft.Network/publicIPAddresses")
-@QueryParams(keys = "api-version", values = "2015-06-15")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
-
 public interface PublicIPAddressApi {
 
    @Named("publicipaddress:list")

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceGroupApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceGroupApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceGroupApi.java
index 1ad47d9..6f718a5 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceGroupApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceGroupApi.java
@@ -19,32 +19,31 @@ import java.io.Closeable;
 import java.net.URI;
 import java.util.List;
 import java.util.Map;
+
 import javax.inject.Named;
 import javax.ws.rs.Consumes;
-import javax.ws.rs.core.MediaType;
 import javax.ws.rs.DELETE;
 import javax.ws.rs.GET;
 import javax.ws.rs.PUT;
 import javax.ws.rs.Path;
 import javax.ws.rs.PathParam;
 import javax.ws.rs.Produces;
+import javax.ws.rs.core.MediaType;
 
 import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
 import org.jclouds.Fallbacks.NullOnNotFoundOr404;
 import org.jclouds.azurecompute.arm.domain.ResourceGroup;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
+import org.jclouds.azurecompute.arm.functions.URIParser;
 import org.jclouds.javax.annotation.Nullable;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
-import org.jclouds.rest.annotations.QueryParams;
-import org.jclouds.rest.annotations.RequestFilters;
-import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.annotations.Fallback;
 import org.jclouds.rest.annotations.MapBinder;
-import org.jclouds.rest.annotations.PayloadParam;
 import org.jclouds.rest.annotations.PATCH;
+import org.jclouds.rest.annotations.PayloadParam;
+import org.jclouds.rest.annotations.RequestFilters;
 import org.jclouds.rest.annotations.ResponseParser;
-import org.jclouds.azurecompute.arm.functions.URIParser;
-
-
+import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.binders.BindToJsonPayload;
 
 /**
@@ -53,9 +52,7 @@ import org.jclouds.rest.binders.BindToJsonPayload;
  * @see <a href="https://msdn.microsoft.com/en-us/library/azure/dn790546.aspx">docs</a>
  */
 @Path("/resourcegroups")
-
-@QueryParams(keys = "api-version", values = "2015-01-01")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface ResourceGroupApi extends Closeable{
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceProviderApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceProviderApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceProviderApi.java
index e3d38b8..a25e2a5 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceProviderApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/ResourceProviderApi.java
@@ -17,14 +17,8 @@
 package org.jclouds.azurecompute.arm.features;
 
 
-import org.jclouds.Fallbacks.NullOnNotFoundOr404;
-import org.jclouds.azurecompute.arm.domain.ResourceProviderMetaData;
-import org.jclouds.javax.annotation.Nullable;
-import org.jclouds.oauth.v2.filters.OAuthFilter;
-import org.jclouds.rest.annotations.Fallback;
-import org.jclouds.rest.annotations.QueryParams;
-import org.jclouds.rest.annotations.RequestFilters;
-import org.jclouds.rest.annotations.SelectJson;
+import java.io.Closeable;
+import java.util.List;
 
 import javax.inject.Named;
 import javax.ws.rs.Consumes;
@@ -32,8 +26,15 @@ import javax.ws.rs.GET;
 import javax.ws.rs.Path;
 import javax.ws.rs.PathParam;
 import javax.ws.rs.core.MediaType;
-import java.io.Closeable;
-import java.util.List;
+
+import org.jclouds.Fallbacks.NullOnNotFoundOr404;
+import org.jclouds.azurecompute.arm.domain.ResourceProviderMetaData;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
+import org.jclouds.javax.annotation.Nullable;
+import org.jclouds.oauth.v2.filters.OAuthFilter;
+import org.jclouds.rest.annotations.Fallback;
+import org.jclouds.rest.annotations.RequestFilters;
+import org.jclouds.rest.annotations.SelectJson;
 
 /**
  * The Azure Resource Provider API provides information about a resource provider and its supported resource types.
@@ -42,8 +43,7 @@ import java.util.List;
  */
 @Path("/providers")
 
-@QueryParams(keys = "api-version", values = "2015-01-01")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface ResourceProviderApi extends Closeable {
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/StorageAccountApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/StorageAccountApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/StorageAccountApi.java
index fd75fca..5d2e06c 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/StorageAccountApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/StorageAccountApi.java
@@ -16,15 +16,19 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
+import java.net.URI;
+import java.util.List;
+import java.util.Map;
+
 import javax.inject.Named;
-import javax.ws.rs.GET;
-import javax.ws.rs.Path;
-import javax.ws.rs.Produces;
 import javax.ws.rs.Consumes;
-import javax.ws.rs.PUT;
-import javax.ws.rs.POST;
 import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.POST;
+import javax.ws.rs.PUT;
+import javax.ws.rs.Path;
 import javax.ws.rs.PathParam;
+import javax.ws.rs.Produces;
 import javax.ws.rs.core.MediaType;
 
 import org.jclouds.Fallbacks;
@@ -32,35 +36,28 @@ import org.jclouds.azurecompute.arm.domain.Availability;
 import org.jclouds.azurecompute.arm.domain.StorageService;
 import org.jclouds.azurecompute.arm.domain.StorageServiceKeys;
 import org.jclouds.azurecompute.arm.domain.StorageServiceUpdateParams;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.azurecompute.arm.functions.FalseOn204;
 import org.jclouds.azurecompute.arm.functions.URIParser;
 import org.jclouds.javax.annotation.Nullable;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
 import org.jclouds.rest.annotations.Fallback;
-import org.jclouds.rest.annotations.QueryParams;
-import org.jclouds.rest.annotations.RequestFilters;
-import org.jclouds.rest.annotations.SelectJson;
-import org.jclouds.rest.annotations.Payload;
+import org.jclouds.rest.annotations.MapBinder;
 import org.jclouds.rest.annotations.PATCH;
-import org.jclouds.rest.annotations.ResponseParser;
+import org.jclouds.rest.annotations.Payload;
 import org.jclouds.rest.annotations.PayloadParam;
-import org.jclouds.rest.annotations.MapBinder;
+import org.jclouds.rest.annotations.RequestFilters;
+import org.jclouds.rest.annotations.ResponseParser;
+import org.jclouds.rest.annotations.SelectJson;
 import org.jclouds.rest.binders.BindToJsonPayload;
 
-import java.util.List;
-import java.util.Map;
-import java.net.URI;
-
-import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.STORAGE_API_VERSION;
-
 /**
  * The Azure Resource Management API includes operations for managing the storage accounts in your subscription.
  *
  * @see <a href="https://msdn.microsoft.com/en-us/library/mt163683.aspx">docs</a>
  */
 @Path("/")
-@RequestFilters(OAuthFilter.class)
-@QueryParams(keys = "api-version", values = STORAGE_API_VERSION)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface StorageAccountApi {
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/SubnetApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/SubnetApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/SubnetApi.java
index 1ac38d8..8f30d6c 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/SubnetApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/SubnetApi.java
@@ -16,20 +16,7 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
-import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
-import org.jclouds.Fallbacks.NullOnNotFoundOr404;
-import org.jclouds.azurecompute.arm.domain.Subnet;
-import org.jclouds.azurecompute.arm.functions.FalseOn204;
-import org.jclouds.oauth.v2.filters.OAuthFilter;
-import org.jclouds.rest.binders.BindToJsonPayload;
-
-import org.jclouds.rest.annotations.Fallback;
-import org.jclouds.rest.annotations.QueryParams;
-import org.jclouds.rest.annotations.RequestFilters;
-import org.jclouds.rest.annotations.SelectJson;
-import org.jclouds.rest.annotations.ResponseParser;
-import org.jclouds.rest.annotations.PayloadParam;
-import org.jclouds.rest.annotations.MapBinder;
+import java.util.List;
 
 import javax.inject.Named;
 import javax.ws.rs.Consumes;
@@ -39,12 +26,24 @@ import javax.ws.rs.PUT;
 import javax.ws.rs.Path;
 import javax.ws.rs.PathParam;
 import javax.ws.rs.core.MediaType;
-import java.util.List;
+
+import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
+import org.jclouds.Fallbacks.NullOnNotFoundOr404;
+import org.jclouds.azurecompute.arm.domain.Subnet;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
+import org.jclouds.azurecompute.arm.functions.FalseOn204;
+import org.jclouds.oauth.v2.filters.OAuthFilter;
+import org.jclouds.rest.annotations.Fallback;
+import org.jclouds.rest.annotations.MapBinder;
+import org.jclouds.rest.annotations.PayloadParam;
+import org.jclouds.rest.annotations.RequestFilters;
+import org.jclouds.rest.annotations.ResponseParser;
+import org.jclouds.rest.annotations.SelectJson;
+import org.jclouds.rest.binders.BindToJsonPayload;
 
 @Path("/resourcegroups/{resourcegroup}/providers/Microsoft.Network/virtualNetworks/{virtualnetwork}/subnets")
 
-@QueryParams(keys = "api-version", values = "2015-06-15")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface SubnetApi {
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VMSizeApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VMSizeApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VMSizeApi.java
index 345e08c..b5917ce 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VMSizeApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VMSizeApi.java
@@ -16,24 +16,24 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
-import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
-import org.jclouds.azurecompute.arm.domain.VMSize;
-import org.jclouds.oauth.v2.filters.OAuthFilter;
-import org.jclouds.rest.annotations.Fallback;
-import org.jclouds.rest.annotations.QueryParams;
-import org.jclouds.rest.annotations.RequestFilters;
-import org.jclouds.rest.annotations.SelectJson;
+import java.util.List;
 
 import javax.inject.Named;
 import javax.ws.rs.Consumes;
 import javax.ws.rs.GET;
 import javax.ws.rs.Path;
 import javax.ws.rs.core.MediaType;
-import java.util.List;
+
+import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
+import org.jclouds.azurecompute.arm.domain.VMSize;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
+import org.jclouds.oauth.v2.filters.OAuthFilter;
+import org.jclouds.rest.annotations.Fallback;
+import org.jclouds.rest.annotations.RequestFilters;
+import org.jclouds.rest.annotations.SelectJson;
 
 @Path("/providers/Microsoft.Compute/locations/{location}/vmSizes")
-@QueryParams(keys = "api-version", values = "2015-06-15")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface VMSizeApi {
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualMachineApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualMachineApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualMachineApi.java
index e0c7e27..2dd6d34 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualMachineApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualMachineApi.java
@@ -34,6 +34,7 @@ import org.jclouds.Fallbacks;
 import org.jclouds.azurecompute.arm.domain.VirtualMachine;
 import org.jclouds.azurecompute.arm.domain.VirtualMachineInstance;
 import org.jclouds.azurecompute.arm.domain.VirtualMachineProperties;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
 import org.jclouds.azurecompute.arm.functions.URIParser;
 import org.jclouds.oauth.v2.filters.OAuthFilter;
 import org.jclouds.rest.annotations.Fallback;
@@ -52,7 +53,7 @@ import org.jclouds.rest.binders.BindToJsonPayload;
  * @see <a href="https://msdn.microsoft.com/en-us/library/azure/mt163630.aspx">docs</a>
  */
 @Path("/resourceGroups/{resourceGroup}/providers/Microsoft.Compute/virtualMachines")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface VirtualMachineApi {
 
@@ -62,7 +63,6 @@ public interface VirtualMachineApi {
    @Named("GetVirtualMachine")
    @GET
    @Path("/{name}")
-   @QueryParams(keys = "api-version", values = "2016-03-30")
    @Fallback(Fallbacks.NullOnNotFoundOr404.class)
    VirtualMachine get(@PathParam("name") String name);
 
@@ -72,7 +72,6 @@ public interface VirtualMachineApi {
    @Named("GetVirtualMachineInstance")
    @GET
    @Path("/{name}/instanceView")
-   @QueryParams(keys = "api-version", values = "2016-03-30")
    @Fallback(Fallbacks.NullOnNotFoundOr404.class)
    VirtualMachineInstance getInstanceDetails(@PathParam("name") String name);
    
@@ -84,7 +83,7 @@ public interface VirtualMachineApi {
    @Payload("%7B\"location\":\"{location}\",\"tags\":%7B%7D,\"properties\":{properties}%7D")
    @MapBinder(BindToJsonPayload.class)
    @Path("/{vmname}")
-   @QueryParams(keys = { "validating", "api-version"}, values = {"false", "2016-03-30"})
+   @QueryParams(keys = "validating", values = "false")
    @Produces(MediaType.APPLICATION_JSON)
    VirtualMachine create(@PathParam("vmname") String vmname,
                          @PayloadParam("location") String location,
@@ -97,7 +96,6 @@ public interface VirtualMachineApi {
    @GET
    @SelectJson("value")
    @Fallback(Fallbacks.EmptyListOnNotFoundOr404.class)
-   @QueryParams(keys = "api-version", values = "2016-06-01" )
    List<VirtualMachine> list();
 
    /**
@@ -107,7 +105,6 @@ public interface VirtualMachineApi {
    @DELETE
    @Path("/{name}")
    @ResponseParser(URIParser.class)
-   @QueryParams(keys = "api-version", values = "2016-03-30")
    @Fallback(Fallbacks.NullOnNotFoundOr404.class)
    URI delete(@PathParam("name") String name);
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApi.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApi.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApi.java
index 0acbdee..1e657f3 100644
--- a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApi.java
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApi.java
@@ -15,22 +15,7 @@
  * limitations under the License.
  */
 package org.jclouds.azurecompute.arm.features;
-import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
-import org.jclouds.Fallbacks.NullOnNotFoundOr404;
-
-import org.jclouds.azurecompute.arm.domain.VirtualNetwork;
-
-import org.jclouds.azurecompute.arm.functions.FalseOn204;
-import org.jclouds.oauth.v2.filters.OAuthFilter;
-
-import org.jclouds.rest.annotations.Fallback;
-import org.jclouds.rest.annotations.QueryParams;
-import org.jclouds.rest.annotations.RequestFilters;
-import org.jclouds.rest.annotations.SelectJson;
-import org.jclouds.rest.annotations.ResponseParser;
-import org.jclouds.rest.annotations.PayloadParam;
-import org.jclouds.rest.annotations.MapBinder;
-import org.jclouds.rest.binders.BindToJsonPayload;
+import java.util.List;
 
 import javax.inject.Named;
 import javax.ws.rs.Consumes;
@@ -40,11 +25,23 @@ import javax.ws.rs.PUT;
 import javax.ws.rs.Path;
 import javax.ws.rs.PathParam;
 import javax.ws.rs.core.MediaType;
-import java.util.List;
+
+import org.jclouds.Fallbacks.EmptyListOnNotFoundOr404;
+import org.jclouds.Fallbacks.NullOnNotFoundOr404;
+import org.jclouds.azurecompute.arm.domain.VirtualNetwork;
+import org.jclouds.azurecompute.arm.filters.ApiVersionFilter;
+import org.jclouds.azurecompute.arm.functions.FalseOn204;
+import org.jclouds.oauth.v2.filters.OAuthFilter;
+import org.jclouds.rest.annotations.Fallback;
+import org.jclouds.rest.annotations.MapBinder;
+import org.jclouds.rest.annotations.PayloadParam;
+import org.jclouds.rest.annotations.RequestFilters;
+import org.jclouds.rest.annotations.ResponseParser;
+import org.jclouds.rest.annotations.SelectJson;
+import org.jclouds.rest.binders.BindToJsonPayload;
 
 @Path("/resourcegroups/{resourcegroup}/providers/Microsoft.Network/virtualNetworks")
-@QueryParams(keys = "api-version", values = "2015-06-15")
-@RequestFilters(OAuthFilter.class)
+@RequestFilters({ OAuthFilter.class, ApiVersionFilter.class })
 @Consumes(MediaType.APPLICATION_JSON)
 public interface VirtualNetworkApi {
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/filters/ApiVersionFilter.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/filters/ApiVersionFilter.java b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/filters/ApiVersionFilter.java
new file mode 100644
index 0000000..f03950b
--- /dev/null
+++ b/azurecompute-arm/src/main/java/org/jclouds/azurecompute/arm/filters/ApiVersionFilter.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.azurecompute.arm.filters;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.API_VERSION_PREFIX;
+import static org.jclouds.util.Maps2.transformKeys;
+import static org.jclouds.util.Predicates2.startsWith;
+
+import java.util.Map;
+
+import javax.inject.Inject;
+
+import org.jclouds.http.HttpException;
+import org.jclouds.http.HttpRequest;
+import org.jclouds.http.HttpRequestFilter;
+import org.jclouds.rest.config.InvocationConfig;
+import org.jclouds.rest.internal.GeneratedHttpRequest;
+
+import com.google.common.base.Function;
+import com.google.common.base.Predicate;
+import com.google.common.reflect.Invokable;
+
+/**
+ * Allow users to customize the api versions for each method call.
+ * <p>
+ * In Azure ARM, each method may have its own api version. This filter allows to
+ * configure the versions of each method, so there is no need to change the code
+ * when Azure deprecates old versions.
+ */
+public class ApiVersionFilter implements HttpRequestFilter {
+
+   private final InvocationConfig config;
+   private final Map<String, String> versions;
+
+   @Inject
+   ApiVersionFilter(InvocationConfig config, Function<Predicate<String>, Map<String, String>> filterStringsBoundByName) {
+      this.config = config;
+      this.versions = versions(filterStringsBoundByName);
+   }
+
+   @Override
+   public HttpRequest filter(HttpRequest request) throws HttpException {
+      checkArgument(request instanceof GeneratedHttpRequest,
+            "This filter can only be applied to GeneratedHttpRequest objects");
+      GeneratedHttpRequest generatedRequest = (GeneratedHttpRequest) request;
+      
+      // Look if there is a custom api version for the current method
+      String commandName = config.getCommandName(generatedRequest.getInvocation());
+      String customApiVersion = versions.get(commandName);
+      
+      if (customApiVersion == null) {
+         // No custom config for the specific method. Let's look for custom config for the class
+         Invokable<?, ?> invoked = generatedRequest.getInvocation().getInvokable();
+         String className = invoked.getOwnerType().getRawType().getSimpleName();
+         customApiVersion = versions.get(className);
+      }
+      
+      if (customApiVersion != null) {
+         return request.toBuilder().replaceQueryParam("api-version", customApiVersion).build();
+      }
+
+      return request;
+   }
+
+   private static final Map<String, String> versions(
+         Function<Predicate<String>, Map<String, String>> filterStringsBoundByName) {
+      Map<String, String> stringBoundWithApiVersionPrefix = filterStringsBoundByName
+            .apply(startsWith(API_VERSION_PREFIX));
+      return transformKeys(stringBoundWithApiVersionPrefix, new Function<String, String>() {
+         public String apply(String input) {
+            return input.replaceFirst(API_VERSION_PREFIX, "");
+         }
+      });
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/DeploymentApiLiveTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/DeploymentApiLiveTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/DeploymentApiLiveTest.java
index fe4c3ee..42116c2 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/DeploymentApiLiveTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/DeploymentApiLiveTest.java
@@ -16,6 +16,10 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
+import static org.testng.Assert.assertNotNull;
+import static org.testng.Assert.assertNull;
+import static org.testng.Assert.assertTrue;
+
 import java.net.URI;
 import java.util.List;
 
@@ -25,18 +29,6 @@ import org.jclouds.azurecompute.arm.domain.Deployment.ProvisioningState;
 import org.jclouds.azurecompute.arm.domain.Subnet;
 import org.jclouds.azurecompute.arm.domain.VirtualNetwork;
 import org.jclouds.azurecompute.arm.internal.BaseAzureComputeApiLiveTest;
-import org.jclouds.compute.domain.Hardware;
-import org.jclouds.compute.domain.HardwareBuilder;
-import org.jclouds.compute.domain.Image;
-import org.jclouds.compute.domain.ImageBuilder;
-import org.jclouds.compute.domain.OperatingSystem;
-import org.jclouds.compute.domain.OsFamily;
-import org.jclouds.compute.domain.Template;
-import org.jclouds.compute.domain.internal.TemplateImpl;
-import org.jclouds.compute.options.TemplateOptions;
-import org.jclouds.domain.Location;
-import org.jclouds.domain.LocationBuilder;
-import org.jclouds.domain.LocationScope;
 import org.jclouds.util.Predicates2;
 import org.testng.Assert;
 import org.testng.annotations.AfterClass;
@@ -46,10 +38,6 @@ import org.testng.annotations.Test;
 import com.google.common.base.Predicate;
 import com.google.common.net.UrlEscapers;
 
-import static org.testng.Assert.assertNotNull;
-import static org.testng.Assert.assertNull;
-import static org.testng.Assert.assertTrue;
-
 @Test(testName = "DeploymentApiLiveTest", singleThreaded = true)
 public class DeploymentApiLiveTest extends BaseAzureComputeApiLiveTest {
 
@@ -109,31 +97,6 @@ public class DeploymentApiLiveTest extends BaseAzureComputeApiLiveTest {
       return body;
    }
 
-   private Template getTemplate(TemplateOptions options) {
-      Location provider = (new LocationBuilder()).scope(LocationScope.PROVIDER).id("azurecompute-arm").description("azurecompute-arm").build();
-      Location region = (new LocationBuilder()).scope(LocationScope.REGION).id(LOCATION).description("West Europe").parent(provider).build();
-
-      OperatingSystem os = OperatingSystem.builder()
-              .family(OsFamily.UBUNTU)
-              .description("14.04.3-LTS")
-              .is64Bit(true)
-              .build();
-
-      Image image = (new ImageBuilder())
-              .id("UbuntuServer14.04.3-LTS")
-              .providerId("Canonical")
-              .name("UbuntuServer")
-              .description("14.04.3-LTS")
-              .version("14.04.3-LTS")
-              .operatingSystem(os)
-              .status(Image.Status.AVAILABLE)
-              .location(region)
-              .build();
-
-      Hardware hardware = (new HardwareBuilder()).id("Standard_A0").build();
-      return new TemplateImpl(image, hardware, region, options);
-   }
-
    @Test
    public void testValidate(){
       Deployment deploymentInvalid = null;

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApiMockTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApiMockTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApiMockTest.java
index adefd95..2d43694 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApiMockTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/NetworkSecurityGroupApiMockTest.java
@@ -83,8 +83,6 @@ public class NetworkSecurityGroupApiMockTest extends BaseAzureComputeApiMockTest
    }
 
    public void getNetworkSecurityGroup() throws InterruptedException {
-      NetworkSecurityGroup nsg = createGroup();
-
       server.enqueue(jsonResponse("/networksecuritygroupget.json").setResponseCode(200));
 
       final NetworkSecurityGroupApi nsgApi = api.getNetworkSecurityGroupApi(resourcegroup);

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApiMockTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApiMockTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApiMockTest.java
index 436cb91..b510580 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApiMockTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/PublicIPAddressApiMockTest.java
@@ -147,8 +147,7 @@ public class PublicIPAddressApiMockTest extends BaseAzureComputeApiMockTest {
       PublicIPAddressProperties properties = PublicIPAddressProperties.create(null, null, "Static", 4, null,
               DnsSettings.create("foobar", "foobar.northeurope.cloudapp.azure.com", null));
 
-      PublicIPAddress ip = ipApi.createOrUpdate(publicIpName, location, tags, properties);
-
+      ipApi.createOrUpdate(publicIpName, location, tags, properties);
    }
 
    public void deletePublicIPAddress() throws InterruptedException {

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/ResourceProviderAPIMockTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/ResourceProviderAPIMockTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/ResourceProviderAPIMockTest.java
index 70f2ad6..3c90d42 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/ResourceProviderAPIMockTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/ResourceProviderAPIMockTest.java
@@ -31,7 +31,6 @@ public class ResourceProviderAPIMockTest extends BaseAzureComputeApiMockTest {
 
    final String apiVersion = "2015-01-01";
    final String resource = "Microsoft.Compute";
-   private final String vm_resource = "virtualMachines";
 
    public void getPublicIPAddressInfo() throws InterruptedException {
       server.enqueue(jsonResponse("/getresourceprovidermetadata.json"));

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/StorageAccountApiMockTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/StorageAccountApiMockTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/StorageAccountApiMockTest.java
index 39ecd2b..e3fdf6d 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/StorageAccountApiMockTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/StorageAccountApiMockTest.java
@@ -235,41 +235,6 @@ public class StorageAccountApiMockTest extends BaseAzureComputeApiMockTest {
               "/providers/Microsoft.Storage/storageAccounts/TESTSTORAGE?api-version=2015-06-15");
    }
 
-   private StorageService getStrorageAccount() {
-      DateService DATE_SERVICE = new SimpleDateFormatDateService();
-      Map<String, String> endpoints = new HashMap<String, String>();
-      endpoints.put("blob", "https://TESTSTORAGE.blob.core.windows.net/");
-      endpoints.put("file", "https://TESTSTORAGE.file.core.windows.net/");
-      endpoints.put("queue", "https://TESTSTORAGE.queue.core.windows.net/");
-      endpoints.put("table", "https://TESTSTORAGE.table.core.windows.net/");
-      Map<String, String> secondaryEndpoints = new HashMap<String, String>();
-      secondaryEndpoints.put("blob", "https://TESTSTORAGE-secondary.blob.core.windows.net/");
-      secondaryEndpoints.put("queue", "https://TESTSTORAGE-secondary.queue.core.windows.net/");
-      secondaryEndpoints.put("table", "https://TESTSTORAGE-secondary.table.core.windows.net/");
-
-
-      String location = "westus";
-      String secondaryLocation = "eastus";
-      final StorageService.StorageServiceProperties props = StorageService.StorageServiceProperties.create(
-              StorageService.AccountType.Standard_RAGRS,
-              DATE_SERVICE.iso8601DateOrSecondsDateParse("2016-02-24T13:04:45.0890883Z"),
-              endpoints,
-              location,
-              StorageService.Status.Succeeded,
-              secondaryEndpoints, secondaryLocation,
-              StorageService.RegionStatus.Available,
-              StorageService.RegionStatus.Available);
-
-      final Map<String, String> tags = ImmutableMap.of(
-              "key1", "value1",
-              "key2", "value2");
-
-      return StorageService.create(
-              "/subscriptions/SUBSCRIPTIONID/resourceGroups/resourceGroup" +
-                      "/providers/Microsoft.Storage/storageAccounts/TESTSTORAGE",
-              "TESTSTORAGE", location, tags, null, props);
-   }
-
    private List<StorageService> expected() throws MalformedURLException {
       DateService DATE_SERVICE = new SimpleDateFormatDateService();
       Map<String, String> endpoints = new HashMap<String, String>();

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/SubnetApiMockTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/SubnetApiMockTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/SubnetApiMockTest.java
index bfcf188..0113201 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/SubnetApiMockTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/SubnetApiMockTest.java
@@ -16,18 +16,17 @@
  */
 package org.jclouds.azurecompute.arm.features;
 
-import com.squareup.okhttp.mockwebserver.RecordedRequest;
-import org.jclouds.azurecompute.arm.domain.Subnet;
-import org.jclouds.azurecompute.arm.internal.BaseAzureComputeApiMockTest;
-import org.testng.annotations.Test;
-
-import java.util.List;
-
 import static com.google.common.collect.Iterables.isEmpty;
 import static org.testng.Assert.assertEquals;
 import static org.testng.Assert.assertFalse;
-import static org.testng.Assert.assertTrue;
 import static org.testng.Assert.assertNull;
+import static org.testng.Assert.assertTrue;
+
+import java.util.List;
+
+import org.jclouds.azurecompute.arm.domain.Subnet;
+import org.jclouds.azurecompute.arm.internal.BaseAzureComputeApiMockTest;
+import org.testng.annotations.Test;
 
 
 @Test(groups = "unit", testName = "SubnetApiMockTest", singleThreaded = true)
@@ -135,6 +134,6 @@ public class SubnetApiMockTest extends BaseAzureComputeApiMockTest {
       assertFalse(status);
 
       String path = String.format("/subscriptions/%s/resourcegroups/%s/providers/Microsoft.Network/virtualNetworks/%s/subnets/%s?%s", subscriptionid, resourcegroup, virtualNetwork, subnetName, apiVersion);
-      RecordedRequest rr = assertSent(server, "DELETE", path);
+      assertSent(server, "DELETE", path);
    }
 }

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiLiveTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiLiveTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiLiveTest.java
index d759760..087c6ef 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiLiveTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiLiveTest.java
@@ -261,10 +261,6 @@ public class VirtualMachineApiLiveTest extends BaseAzureComputeApiLiveTest {
       return api.getNetworkInterfaceCardApi(resourceGroupName).createOrUpdate(networkInterfaceCardName, locationName, networkInterfaceCardProperties, tags);
    }
 
-   private boolean deleteStorageService(String resourceGroupName, String storageServiceName) {
-      return api.getStorageAccountApi(resourceGroupName).delete(storageServiceName);
-   }
-
    private boolean waitForState(String name, final String state, final String displayStatus) {
       return FluentIterable.from(api().getInstanceDetails(name).statuses())
               .filter(new Predicate<VirtualMachineInstance.VirtualMachineStatus>() {

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiMockTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiMockTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiMockTest.java
index 9e1bd7a..c85a103 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiMockTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualMachineApiMockTest.java
@@ -56,14 +56,14 @@ public class VirtualMachineApiMockTest extends BaseAzureComputeApiMockTest {
       final VirtualMachineApi vmAPI = api.getVirtualMachineApi("groupname");
       assertEquals(vmAPI.get("windowsmachine"), getVM());
       assertSent(server, "GET", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines/windowsmachine?api-version=2015-06-15");
+              "/virtualMachines/windowsmachine?api-version=2016-03-30");
    }
    public void testGetEmpty() throws Exception {
       server.enqueue(new MockResponse().setResponseCode(404));
       final VirtualMachineApi vmAPI = api.getVirtualMachineApi("groupname");
       assertNull(vmAPI.get("windowsmachine"));
       assertSent(server, "GET", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines/windowsmachine?api-version=2015-06-15");
+              "/virtualMachines/windowsmachine?api-version=2016-03-30");
    }
 
    public void testGetInstanceDetails() throws Exception {
@@ -77,7 +77,7 @@ public class VirtualMachineApiMockTest extends BaseAzureComputeApiMockTest {
       assertEquals(actual.statuses().get(0).level(), expected.statuses().get(0).level());
       //assertEquals(actual.statuses().get(0).time().toString(), expected.statuses().get(0).time().toString());
       assertSent(server, "GET", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines/windowsmachine/instanceView?api-version=2015-06-15");
+              "/virtualMachines/windowsmachine/instanceView?api-version=2016-03-30");
    }
 
    public void testGetInstanceDetailsEmpty() throws Exception {
@@ -85,7 +85,7 @@ public class VirtualMachineApiMockTest extends BaseAzureComputeApiMockTest {
       final VirtualMachineApi vmAPI = api.getVirtualMachineApi("groupname");
       assertNull(vmAPI.getInstanceDetails("windowsmachine"));
       assertSent(server, "GET", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines/windowsmachine/instanceView?api-version=2015-06-15");
+              "/virtualMachines/windowsmachine/instanceView?api-version=2016-03-30");
    }
 
    public void testList() throws Exception {
@@ -93,14 +93,14 @@ public class VirtualMachineApiMockTest extends BaseAzureComputeApiMockTest {
       final VirtualMachineApi vmAPI = api.getVirtualMachineApi("groupname");
       assertEquals(vmAPI.list(), getVMList());
       assertSent(server, "GET", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines?api-version=2015-06-15");
+              "/virtualMachines?api-version=2016-06-01");
    }
    public void testListEmpty() throws Exception {
       server.enqueue(new MockResponse().setResponseCode(404));
       final VirtualMachineApi vmAPI = api.getVirtualMachineApi("groupname");
       assertTrue(isEmpty(vmAPI.list()));
       assertSent(server, "GET", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines?api-version=2015-06-15");
+              "/virtualMachines?api-version=2016-06-01");
    }
 
    public void testCreate() throws Exception {
@@ -110,7 +110,7 @@ public class VirtualMachineApiMockTest extends BaseAzureComputeApiMockTest {
       VirtualMachine vm = vmAPI.create("windowsmachine", "westus", getProperties());
       assertEquals(vm, getVM());
       assertSent(server, "PUT", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines/windowsmachine?api-version=2015-06-15&validating=false",
+              "/virtualMachines/windowsmachine?validating=false&api-version=2016-03-30",
               "{\"location\":\"westus\",\"properties\":" +
                       "{\"vmId\":\"27ee085b-d707-xxxx-yyyy-2370e2eb1cc1\"," +
                       "\"hardwareProfile\":{\"vmSize\":\"Standard_D1\"}," +
@@ -134,7 +134,7 @@ public class VirtualMachineApiMockTest extends BaseAzureComputeApiMockTest {
       assertNull(uri);
 
       assertSent(server, "DELETE", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines/windowsmachine?api-version=2015-06-15");
+              "/virtualMachines/windowsmachine?api-version=2016-03-30");
    }
    public void testDelete() throws Exception {
       server.enqueue(response202WithHeader());
@@ -147,7 +147,7 @@ public class VirtualMachineApiMockTest extends BaseAzureComputeApiMockTest {
       assertNotNull(uri);
 
       assertSent(server, "DELETE", "/subscriptions/SUBSCRIPTIONID/resourceGroups/groupname/providers/Microsoft.Compute" +
-              "/virtualMachines/windowsmachine?api-version=2015-06-15");
+              "/virtualMachines/windowsmachine?api-version=2016-03-30");
    }
 
    public void testStart() throws Exception {

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApiMockTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApiMockTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApiMockTest.java
index 99b0b57..79b48ef 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApiMockTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/features/VirtualNetworkApiMockTest.java
@@ -101,7 +101,7 @@ public class VirtualNetworkApiMockTest extends BaseAzureComputeApiMockTest {
                       VirtualNetwork.AddressSpace.create(Arrays.asList("10.2.0.0/16")), null);
 
 
-      VirtualNetwork vn = vnApi.createOrUpdate(virtualNetwork, location, virtualNetworkProperties);
+      vnApi.createOrUpdate(virtualNetwork, location, virtualNetworkProperties);
 
       String path = String.format("/subscriptions/%s/resourcegroups/%s/providers/Microsoft.Network/virtualNetworks/%s?%s", subscriptionid, resourcegroup, virtualNetwork, apiVersion);
       String json = String.format("{\"location\":\"%s\",\"properties\":{\"addressSpace\":{\"addressPrefixes\":[\"%s\"]}}}", location, "10.2.0.0/16");

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/filters/ApiVersionFilterTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/filters/ApiVersionFilterTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/filters/ApiVersionFilterTest.java
new file mode 100644
index 0000000..f3b15ce
--- /dev/null
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/filters/ApiVersionFilterTest.java
@@ -0,0 +1,129 @@
+/*
+ * 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.filters;
+
+import static org.easymock.EasyMock.createMock;
+import static org.easymock.EasyMock.expect;
+import static org.easymock.EasyMock.replay;
+import static org.jclouds.azurecompute.arm.config.AzureComputeProperties.API_VERSION_PREFIX;
+import static org.jclouds.reflect.Reflection2.method;
+import static org.testng.Assert.assertEquals;
+
+import java.util.Properties;
+
+import javax.inject.Named;
+
+import org.jclouds.http.HttpRequest;
+import org.jclouds.http.HttpResponse;
+import org.jclouds.internal.FilterStringsBoundToInjectorByName;
+import org.jclouds.reflect.Invocation;
+import org.jclouds.rest.config.InvocationConfig;
+import org.jclouds.rest.internal.GeneratedHttpRequest;
+import org.testng.annotations.BeforeMethod;
+import org.testng.annotations.Test;
+
+import com.google.common.collect.ImmutableList;
+import com.google.inject.AbstractModule;
+import com.google.inject.Guice;
+import com.google.inject.Injector;
+import com.google.inject.name.Names;
+
+@Test(groups = "unit", testName = "ApiVersionFilterTest", singleThreaded = true)
+public class ApiVersionFilterTest {
+
+   public interface VersionedApi {
+      HttpResponse noName();
+
+      @Named("named:get")
+      HttpResponse named();
+   }
+
+   private Invocation noName;
+   private Invocation named;
+   private InvocationConfig config;
+
+   @BeforeMethod
+   public void setup() {
+      noName = Invocation.create(method(VersionedApi.class, "noName"), ImmutableList.of());
+      named = Invocation.create(method(VersionedApi.class, "named"), ImmutableList.of());
+
+      config = createMock(InvocationConfig.class);
+      expect(config.getCommandName(noName)).andReturn("VersionedApi.noName");
+      expect(config.getCommandName(named)).andReturn("named:get");
+      replay(config);
+   }
+
+   @Test(expectedExceptions = IllegalArgumentException.class)
+   public void testFailIfNoGeneratedHttpRequest() {
+      ApiVersionFilter filter = new ApiVersionFilter(config, filterStringsBoundToInjectorByName(new Properties()));
+      filter.filter(HttpRequest.builder().method("GET").endpoint("http://localhost").build());
+   }
+
+   @Test
+   public void testOverrideMethodVersion() {
+      Properties props = new Properties();
+      props.setProperty(API_VERSION_PREFIX + "named:get", "namedversion");
+      props.setProperty(API_VERSION_PREFIX + "VersionedApi.noName", "noNameversion");
+      ApiVersionFilter filter = new ApiVersionFilter(config, filterStringsBoundToInjectorByName(props));
+
+      HttpRequest request = GeneratedHttpRequest.builder().method("GET").endpoint("http://localhost")
+            .invocation(noName).addQueryParam("api-version", "original", "original2").build();
+      HttpRequest filtered = filter.filter(request);
+      assertEquals(filtered.getEndpoint().getQuery(), "api-version=noNameversion");
+
+      request = GeneratedHttpRequest.builder().method("GET").endpoint("http://localhost").invocation(named)
+            .addQueryParam("api-version", "original", "original2").build();
+      filtered = filter.filter(request);
+      assertEquals(filtered.getEndpoint().getQuery(), "api-version=namedversion");
+   }
+
+   @Test
+   public void testFallbackToClassName() {
+      Properties props = new Properties();
+      props.setProperty(API_VERSION_PREFIX + "VersionedApi", "classversion");
+      ApiVersionFilter filter = new ApiVersionFilter(config, filterStringsBoundToInjectorByName(props));
+
+      HttpRequest request = GeneratedHttpRequest.builder().method("GET").endpoint("http://localhost")
+            .invocation(noName).addQueryParam("api-version", "original", "original2").build();
+      HttpRequest filtered = filter.filter(request);
+      assertEquals(filtered.getEndpoint().getQuery(), "api-version=classversion");
+
+      request = GeneratedHttpRequest.builder().method("GET").endpoint("http://localhost").invocation(named)
+            .addQueryParam("api-version", "original", "original2").build();
+      filtered = filter.filter(request);
+      assertEquals(filtered.getEndpoint().getQuery(), "api-version=classversion");
+   }
+
+   @Test
+   public void testNothingChangesIfNoCustomVersion() {
+      ApiVersionFilter filter = new ApiVersionFilter(config, filterStringsBoundToInjectorByName(new Properties()));
+
+      HttpRequest request = GeneratedHttpRequest.builder().method("GET").endpoint("http://localhost").invocation(named)
+            .addQueryParam("api-version", "foo").build();
+      HttpRequest filtered = filter.filter(request);
+      assertEquals(filtered.getEndpoint().getQuery(), "api-version=foo");
+   }
+
+   private FilterStringsBoundToInjectorByName filterStringsBoundToInjectorByName(final Properties props) {
+      Injector injector = Guice.createInjector(new AbstractModule() {
+         protected void configure() {
+            Names.bindProperties(binder(), props);
+         }
+      });
+      return new FilterStringsBoundToInjectorByName(injector);
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs/blob/8d0cd4d8/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/internal/BaseAzureComputeApiMockTest.java
----------------------------------------------------------------------
diff --git a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/internal/BaseAzureComputeApiMockTest.java b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/internal/BaseAzureComputeApiMockTest.java
index 5c60f54..dc4ad28 100644
--- a/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/internal/BaseAzureComputeApiMockTest.java
+++ b/azurecompute-arm/src/test/java/org/jclouds/azurecompute/arm/internal/BaseAzureComputeApiMockTest.java
@@ -60,18 +60,22 @@ public class BaseAzureComputeApiMockTest {
    public void start() throws IOException {
       server = new MockWebServer();
       server.play();
-      Properties properties = new Properties();
-      properties.put(CREDENTIAL_TYPE, BEARER_TOKEN_CREDENTIALS.toString());
-      properties.put("oauth.endpoint", "https://login.microsoftonline.com/tenant-id/oauth2/token");
       AzureComputeProviderMetadata pm = AzureComputeProviderMetadata.builder().build();
       context = ContextBuilder.newBuilder(pm)
               .credentials("", MOCK_BEARER_TOKEN)
               .endpoint(server.getUrl("/").toString() + "subscriptions/SUBSCRIPTIONID")
               .modules(modules)
-              .overrides(properties)
+              .overrides(setupProperties())
               .build();
       api = context.getApi();
    }
+   
+   protected Properties setupProperties() {
+      Properties properties = new Properties();
+      properties.put(CREDENTIAL_TYPE, BEARER_TOKEN_CREDENTIALS.toString());
+      properties.put("oauth.endpoint", "https://login.microsoftonline.com/tenant-id/oauth2/token");
+      return properties;
+   }
 
    @AfterMethod(alwaysRun = true)
    public void stop() throws IOException {