From 4596471bb258c391af06b7bde6f017af02e965db Mon Sep 17 00:00:00 2001 From: Ignasi Barrera Date: Fri, 23 Oct 2015 00:18:45 +0200 Subject: [PATCH] JCLOUDS-1025: Add support for metadata and tags in the ComputeService --- .../DigitalOcean2ComputeServiceAdapter.java | 21 +++++++++++++++- .../compute/functions/RegionToLocation.java | 2 ++ .../domain/options/CreateDropletOptions.java | 24 +++++++++++++++++++ .../DigitalOcean2ComputeServiceLiveTest.java | 4 ++-- .../functions/RegionToLocationTest.java | 10 +++++--- 5 files changed, 55 insertions(+), 6 deletions(-) diff --git a/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/compute/DigitalOcean2ComputeServiceAdapter.java b/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/compute/DigitalOcean2ComputeServiceAdapter.java index f1f5919a9b..43b158524c 100644 --- a/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/compute/DigitalOcean2ComputeServiceAdapter.java +++ b/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/compute/DigitalOcean2ComputeServiceAdapter.java @@ -27,7 +27,10 @@ import static com.google.common.collect.Sets.newHashSet; import static org.jclouds.compute.config.ComputeServiceProperties.TIMEOUT_NODE_RUNNING; import static org.jclouds.compute.config.ComputeServiceProperties.TIMEOUT_NODE_SUSPENDED; import static org.jclouds.compute.config.ComputeServiceProperties.TIMEOUT_NODE_TERMINATED; +import static org.jclouds.compute.util.ComputeServiceUtils.metadataAndTagsAsCommaDelimitedValue; +import java.util.List; +import java.util.Map; import java.util.Set; import javax.annotation.Resource; @@ -48,6 +51,7 @@ import org.jclouds.digitalocean2.domain.Region; import org.jclouds.digitalocean2.domain.Size; import org.jclouds.digitalocean2.domain.options.CreateDropletOptions; import org.jclouds.domain.LoginCredentials; +import org.jclouds.json.Json; import org.jclouds.logging.Logger; import com.google.common.base.Function; @@ -67,15 +71,18 @@ public class DigitalOcean2ComputeServiceAdapter implements ComputeServiceAdapter private final Predicate nodeRunningPredicate; private final Predicate nodeStoppedPredicate; private final Predicate nodeTerminatedPredicate; + private final Json json; @Inject DigitalOcean2ComputeServiceAdapter(DigitalOcean2Api api, @Named(TIMEOUT_NODE_RUNNING) Predicate nodeRunningPredicate, @Named(TIMEOUT_NODE_SUSPENDED) Predicate nodeStoppedPredicate, - @Named(TIMEOUT_NODE_TERMINATED) Predicate nodeTerminatedPredicate) { + @Named(TIMEOUT_NODE_TERMINATED) Predicate nodeTerminatedPredicate, + Json json) { this.api = api; this.nodeRunningPredicate = nodeRunningPredicate; this.nodeStoppedPredicate = nodeStoppedPredicate; this.nodeTerminatedPredicate = nodeTerminatedPredicate; + this.json = json; } @Override @@ -91,6 +98,18 @@ public class DigitalOcean2ComputeServiceAdapter implements ComputeServiceAdapter options.addSshKeyIds(templateOptions.getSshKeyIds()); } + Map metadataAndTags = metadataAndTagsAsCommaDelimitedValue(templateOptions); + if (!metadataAndTags.isEmpty()) { + @SuppressWarnings("unchecked") + List regionFeatures = (List) template.getLocation().getMetadata().get("features"); + if (regionFeatures.contains("metadata")) { + options.userData(json.toJson(metadataAndTags)); + } else { + logger.debug(">> region %s does not support metadata, ignoring provided user data", template.getLocation() + .getId()); + } + } + DropletCreate dropletCreated = api.dropletApi().create(name, template.getLocation().getId(), template.getHardware().getProviderId(), diff --git a/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/compute/functions/RegionToLocation.java b/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/compute/functions/RegionToLocation.java index 4adf240f8c..adde1b7ce1 100644 --- a/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/compute/functions/RegionToLocation.java +++ b/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/compute/functions/RegionToLocation.java @@ -29,6 +29,7 @@ import org.jclouds.domain.LocationScope; import org.jclouds.location.suppliers.all.JustProvider; import com.google.common.base.Function; +import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableSet; /** @@ -52,6 +53,7 @@ public class RegionToLocation implements Function { builder.scope(LocationScope.REGION); builder.parent(getOnlyElement(justProvider.get())); builder.iso3166Codes(ImmutableSet. of()); + builder.metadata(ImmutableMap. of("available", input.available(), "features", input.features())); return builder.build(); } } diff --git a/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/domain/options/CreateDropletOptions.java b/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/domain/options/CreateDropletOptions.java index b20fc96b72..91fb09073a 100644 --- a/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/domain/options/CreateDropletOptions.java +++ b/providers/digitalocean2/src/main/java/org/jclouds/digitalocean2/domain/options/CreateDropletOptions.java @@ -104,6 +104,14 @@ public class CreateDropletOptions implements MapBinder { return backupsEnabled; } + public boolean isIpv6Enabled() { + return ipv6Enabled; + } + + public String getUserData() { + return userData; + } + public static Builder builder() { return new Builder(); } @@ -148,6 +156,22 @@ public class CreateDropletOptions implements MapBinder { return this; } + /** + * Sets the user data for the droplet. + */ + public Builder userData(String userData) { + this.userData = userData; + return this; + } + + /** + * Enables/disables IPv6 for the droplet. + */ + public Builder ipv6Enabled(boolean ipv6Enabled) { + this.ipv6Enabled = ipv6Enabled; + return this; + } + public CreateDropletOptions build() { return new CreateDropletOptions(sshKeyIds.build(), backupsEnabled, ipv6Enabled, privateNetworking, userData); } diff --git a/providers/digitalocean2/src/test/java/org/jclouds/digitalocean2/compute/DigitalOcean2ComputeServiceLiveTest.java b/providers/digitalocean2/src/test/java/org/jclouds/digitalocean2/compute/DigitalOcean2ComputeServiceLiveTest.java index b1dcc1bc97..b8fbbe7963 100644 --- a/providers/digitalocean2/src/test/java/org/jclouds/digitalocean2/compute/DigitalOcean2ComputeServiceLiveTest.java +++ b/providers/digitalocean2/src/test/java/org/jclouds/digitalocean2/compute/DigitalOcean2ComputeServiceLiveTest.java @@ -47,12 +47,12 @@ public class DigitalOcean2ComputeServiceLiveTest extends BaseComputeServiceLiveT @Override protected void checkTagsInNodeEquals(NodeMetadata node, ImmutableSet tags) { - // DigitalOcean does not support tags + // We encode the tags in the user data but the DigitalOcean API does not return it } @Override protected void checkUserMetadataContains(NodeMetadata node, ImmutableMap userMetadata) { - // DigitalOcean does not support user metadata + // The DigitalOcean API does not return the user data } } diff --git a/providers/digitalocean2/src/test/java/org/jclouds/digitalocean2/compute/functions/RegionToLocationTest.java b/providers/digitalocean2/src/test/java/org/jclouds/digitalocean2/compute/functions/RegionToLocationTest.java index 879091ba39..7e6eceae1a 100644 --- a/providers/digitalocean2/src/test/java/org/jclouds/digitalocean2/compute/functions/RegionToLocationTest.java +++ b/providers/digitalocean2/src/test/java/org/jclouds/digitalocean2/compute/functions/RegionToLocationTest.java @@ -42,11 +42,15 @@ public class RegionToLocationTest { JustProvider locationsSupplier = new JustProvider(metadata.getId(), Suppliers. ofInstance(URI .create(metadata.getEndpoint())), ImmutableSet. of()); - Region region = Region.create("reg1", "Region1", ImmutableList. of(), true, ImmutableList. of()); + Region region = Region.create("reg1", "Region1", ImmutableList. of(), true, + ImmutableList. of("virtio", "metadata")); Location expected = new LocationBuilder().id("reg1").description("reg1/Region 1") .parent(getOnlyElement(locationsSupplier.get())).scope(LocationScope.REGION).build(); - RegionToLocation function = new RegionToLocation(locationsSupplier); - assertEquals(function.apply(region), expected); + Location location = new RegionToLocation(locationsSupplier).apply(region); + + assertEquals(location, expected); + assertEquals(location.getMetadata().get("available"), true); + assertEquals(location.getMetadata().get("features"), ImmutableList.of("virtio", "metadata")); } }