diff --git a/apis/ec2/src/main/java/org/jclouds/ec2/options/DescribeImagesOptions.java b/apis/ec2/src/main/java/org/jclouds/ec2/options/DescribeImagesOptions.java index b84b5c836f..5e5f1d6182 100644 --- a/apis/ec2/src/main/java/org/jclouds/ec2/options/DescribeImagesOptions.java +++ b/apis/ec2/src/main/java/org/jclouds/ec2/options/DescribeImagesOptions.java @@ -66,6 +66,11 @@ public class DescribeImagesOptions extends BaseEC2RequestOptions { return this; } + public DescribeImagesOptions imageIds(Iterable imageIds) { + indexFormValuesWithPrefix("ImageId", imageIds); + return this; + } + public Set getImageIds() { return getFormValuesWithKeysPrefixedBy("ImageId."); } diff --git a/providers/aws-ec2/src/main/java/org/jclouds/aws/ec2/options/AWSDescribeImagesOptions.java b/providers/aws-ec2/src/main/java/org/jclouds/aws/ec2/options/AWSDescribeImagesOptions.java new file mode 100644 index 0000000000..9b8f6cffab --- /dev/null +++ b/providers/aws-ec2/src/main/java/org/jclouds/aws/ec2/options/AWSDescribeImagesOptions.java @@ -0,0 +1,154 @@ +/** + * + * Copyright (C) 2011 Cloud Conscious, LLC. + * + * ==================================================================== + * Licensed 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.aws.ec2.options; + +import static com.google.common.base.Preconditions.checkNotNull; + +import java.util.Collection; +import java.util.Map; +import java.util.Map.Entry; + +import org.jclouds.ec2.options.DescribeImagesOptions; + +import com.google.common.collect.Multimap; +import com.google.common.collect.Multimaps; + +/** + * Extra options only available in Amazon's implementation + * + * @see DescribeImagesOptions + * @author Adrian Cole + */ +public class AWSDescribeImagesOptions extends DescribeImagesOptions { + public static final AWSDescribeImagesOptions NONE = new AWSDescribeImagesOptions(); + + /** + * {@inheritDoc} + */ + @Override + public AWSDescribeImagesOptions executableBy(String identityId) { + super.executableBy(identityId); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public AWSDescribeImagesOptions imageIds(String... imageIds) { + super.imageIds(imageIds); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public AWSDescribeImagesOptions imageIds(Iterable imageIds) { + super.imageIds(imageIds); + return this; + } + + /** + * {@inheritDoc} + */ + @Override + public AWSDescribeImagesOptions ownedBy(String... owners) { + super.ownedBy(owners); + return this; + } + + /** + * You can filter the results to return information only about images that match criteria you + * specify. For example, you could get information only about images that use a certain kernel. + * You can specify multiple values for a filter (e.g., the image uses either kernel aki-1a2b3c4d + * or kernel aki-9b8c7d6f). An image must match at least one of the specified values for it to be + * included in the results. + *

+ * You can specify multiple filters (e.g., the image uses a certain kernel, and uses an Amazon + * EBS volume as the root device). The result includes information for a particular image only if + * it matches all your filters. If there's no match, no special message is returned; the response + * is simply empty. + *

+ * You can use wildcards with the filter values: * matches zero or more characters, and ? matches + * exactly one character. You can escape special characters using a backslash before the + * character. For example, a value of \*amazon\?\\ searches for the literal string *amazon?\. + * + */ + public AWSDescribeImagesOptions filters(Multimap filters) { + int i = 0; + for (Entry> filter : checkNotNull(filters, "filters").asMap().entrySet()) { + String filterPrefix = String.format("Filter.%s.", ++i); + formParameters.put(filterPrefix + "Name", filter.getKey()); + indexFormValuesWithPrefix(filterPrefix + "Value", filter.getValue()); + } + return this; + } + + /** + * @see #filters(Multimap) + */ + public AWSDescribeImagesOptions filters(Map filters) { + return filters(Multimaps.forMap(checkNotNull(filters, "filters"))); + } + + public static class Builder extends DescribeImagesOptions.Builder { + + /** + * @see AWSDescribeImagesOptions#executableBy + */ + public static AWSDescribeImagesOptions executableBy(String identityId) { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + return options.executableBy(identityId); + } + + /** + * @see AWSDescribeImagesOptions#imageIds + */ + public static AWSDescribeImagesOptions imageIds(String... imageIds) { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + return options.imageIds(imageIds); + } + + /** + * @see AWSDescribeImagesOptions#filters(Multimap) + */ + public static AWSDescribeImagesOptions filters(Multimap filters) { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + return options.filters(filters); + } + + /** + * @see AWSDescribeImagesOptions#filters(Map) + */ + public static AWSDescribeImagesOptions filters(Map filters) { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + return options.filters(filters); + } + + /** + * @see AWSDescribeImagesOptions#ownedBy + */ + public static AWSDescribeImagesOptions ownedBy(String... owners) { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + return options.ownedBy(owners); + } + + } +} diff --git a/providers/aws-ec2/src/test/java/org/jclouds/aws/ec2/options/AWSDescribeImagesOptionsTest.java b/providers/aws-ec2/src/test/java/org/jclouds/aws/ec2/options/AWSDescribeImagesOptionsTest.java new file mode 100644 index 0000000000..505349bef0 --- /dev/null +++ b/providers/aws-ec2/src/test/java/org/jclouds/aws/ec2/options/AWSDescribeImagesOptionsTest.java @@ -0,0 +1,180 @@ +/** + * + * Copyright (C) 2011 Cloud Conscious, LLC. + * + * ==================================================================== + * Licensed 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.aws.ec2.options; + +import static org.jclouds.aws.ec2.options.AWSDescribeImagesOptions.Builder.executableBy; +import static org.jclouds.aws.ec2.options.AWSDescribeImagesOptions.Builder.filters; +import static org.jclouds.aws.ec2.options.AWSDescribeImagesOptions.Builder.imageIds; +import static org.jclouds.aws.ec2.options.AWSDescribeImagesOptions.Builder.ownedBy; +import static org.testng.Assert.assertEquals; + +import java.util.Collections; + +import org.jclouds.http.options.HttpRequestOptions; +import org.testng.annotations.Test; + +import com.google.common.collect.ImmutableMap; +import com.google.common.collect.ImmutableMultimap; + +/** + * Tests possible uses of AWSDescribeImagesOptions and AWSDescribeImagesOptions.Builder.* + * + * @author Adrian Cole + */ +public class AWSDescribeImagesOptionsTest { + + @Test + public void testAssignability() { + assert HttpRequestOptions.class.isAssignableFrom(AWSDescribeImagesOptions.class); + assert !String.class.isAssignableFrom(AWSDescribeImagesOptions.class); + } + + @Test + public void testExecutableBy() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + options.executableBy("test"); + assertEquals(options.buildFormParameters().get("ExecutableBy"), Collections.singletonList("test")); + } + + @Test + public void testNullExecutableBy() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + assertEquals(options.buildFormParameters().get("ExecutableBy"), Collections.EMPTY_LIST); + } + + @Test + public void testExecutableByStatic() { + AWSDescribeImagesOptions options = executableBy("test"); + assertEquals(options.buildFormParameters().get("ExecutableBy"), Collections.singletonList("test")); + } + + @Test(expectedExceptions = NullPointerException.class) + public void testExecutableByNPE() { + executableBy(null); + } + + @Test + public void testOwners() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + options.ownedBy("test"); + assertEquals(options.buildFormParameters().get("Owner.1"), Collections.singletonList("test")); + } + + @Test + public void testMultipleOwners() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + options.ownedBy("test", "trouble"); + assertEquals(options.buildFormParameters().get("Owner.1"), Collections.singletonList("test")); + assertEquals(options.buildFormParameters().get("Owner.2"), Collections.singletonList("trouble")); + } + + @Test + public void testNullOwners() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + assertEquals(options.buildFormParameters().get("Owner.1"), Collections.EMPTY_LIST); + } + + @Test + public void testOwnersStatic() { + AWSDescribeImagesOptions options = ownedBy("test"); + assertEquals(options.buildFormParameters().get("Owner.1"), Collections.singletonList("test")); + } + + public void testNoOwners() { + ownedBy(); + } + + @Test + public void testImageIds() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + options.imageIds("test"); + assertEquals(options.buildFormParameters().get("ImageId.1"), Collections.singletonList("test")); + } + + @Test + public void testMultipleImageIds() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + options.imageIds("test", "trouble"); + assertEquals(options.buildFormParameters().get("ImageId.1"), Collections.singletonList("test")); + assertEquals(options.buildFormParameters().get("ImageId.2"), Collections.singletonList("trouble")); + } + + @Test + public void testNullImageIds() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + assertEquals(options.buildFormParameters().get("ImageId.1"), Collections.EMPTY_LIST); + } + + @Test + public void testImageIdsStatic() { + AWSDescribeImagesOptions options = imageIds("test"); + assertEquals(options.buildFormParameters().get("ImageId.1"), Collections.singletonList("test")); + } + + public void testNoImageIds() { + imageIds(); + } + + @Test + public void testMapFilters() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + options.filters(ImmutableMap.of("is-public", "true", "architecture", "x86_64", "platform", "windows")); + testMapFilters(options); + } + + private void testMapFilters(AWSDescribeImagesOptions options) { + assertEquals(options.buildFormParameters().get("Filter.1.Name"), Collections.singletonList("is-public")); + assertEquals(options.buildFormParameters().get("Filter.1.Value.1"), Collections.singletonList("true")); + assertEquals(options.buildFormParameters().get("Filter.2.Name"), Collections.singletonList("architecture")); + assertEquals(options.buildFormParameters().get("Filter.2.Value.1"), Collections.singletonList("x86_64")); + assertEquals(options.buildFormParameters().get("Filter.3.Name"), Collections.singletonList("platform")); + assertEquals(options.buildFormParameters().get("Filter.3.Value.1"), Collections.singletonList("windows")); + } + + @Test + public void testMapFiltersStatic() { + AWSDescribeImagesOptions options = filters(ImmutableMap.of("is-public", "true", "architecture", "x86_64", + "platform", "windows")); + testMapFilters(options); + } + + + @Test + public void testMultimapFilters() { + AWSDescribeImagesOptions options = new AWSDescribeImagesOptions(); + options.filters(ImmutableMultimap.of("is-public", "true", "architecture", "x86_64", "platform", "windows")); + testMultimapFilters(options); + } + + private void testMultimapFilters(AWSDescribeImagesOptions options) { + assertEquals(options.buildFormParameters().get("Filter.1.Name"), Collections.singletonList("is-public")); + assertEquals(options.buildFormParameters().get("Filter.1.Value.1"), Collections.singletonList("true")); + assertEquals(options.buildFormParameters().get("Filter.2.Name"), Collections.singletonList("architecture")); + assertEquals(options.buildFormParameters().get("Filter.2.Value.1"), Collections.singletonList("x86_64")); + assertEquals(options.buildFormParameters().get("Filter.3.Name"), Collections.singletonList("platform")); + assertEquals(options.buildFormParameters().get("Filter.3.Value.1"), Collections.singletonList("windows")); + } + + @Test + public void testMultimapFiltersStatic() { + AWSDescribeImagesOptions options = filters(ImmutableMultimap.of("is-public", "true", "architecture", "x86_64", + "platform", "windows")); + testMultimapFilters(options); + } +}