Wrap Image with Optional in DiskURIToImage

This commit is contained in:
Tomasz Wojtuń 2017-02-22 08:16:10 +01:00 committed by Ignasi Barrera
parent d89d6b5d05
commit f5a5d869fe
7 changed files with 55 additions and 14 deletions

View File

@ -62,6 +62,7 @@ import org.jclouds.googlecomputeengine.features.InstanceApi;
import org.jclouds.location.suppliers.all.JustProvider; import org.jclouds.location.suppliers.all.JustProvider;
import com.google.common.base.Function; import com.google.common.base.Function;
import com.google.common.base.Optional;
import com.google.common.base.Predicate; import com.google.common.base.Predicate;
import com.google.common.base.Splitter; import com.google.common.base.Splitter;
import com.google.common.base.Strings; import com.google.common.base.Strings;
@ -96,7 +97,7 @@ public final class GoogleComputeEngineServiceAdapter
private final Function<Map<String, ?>, String> windowsPasswordGenerator; private final Function<Map<String, ?>, String> windowsPasswordGenerator;
private final FirewallTagNamingConvention.Factory firewallTagNamingConvention; private final FirewallTagNamingConvention.Factory firewallTagNamingConvention;
private final List<String> imageProjects; private final List<String> imageProjects;
private final LoadingCache<URI, Image> diskURIToImage; private final LoadingCache<URI, Optional<Image>> diskURIToImage;
@Inject GoogleComputeEngineServiceAdapter(JustProvider justProvider, GoogleComputeEngineApi api, @Inject GoogleComputeEngineServiceAdapter(JustProvider justProvider, GoogleComputeEngineApi api,
Predicate<AtomicReference<Operation>> operationDone, Predicate<AtomicReference<Operation>> operationDone,
@ -105,7 +106,7 @@ public final class GoogleComputeEngineServiceAdapter
Resources resources, Resources resources,
FirewallTagNamingConvention.Factory firewallTagNamingConvention, FirewallTagNamingConvention.Factory firewallTagNamingConvention,
@Named(IMAGE_PROJECTS) String imageProjects, @Named(IMAGE_PROJECTS) String imageProjects,
LoadingCache<URI, Image> diskURIToImage) { LoadingCache<URI, Optional<Image>> diskURIToImage) {
this.justProvider = justProvider; this.justProvider = justProvider;
this.api = api; this.api = api;
this.operationDone = operationDone; this.operationDone = operationDone;

View File

@ -67,6 +67,7 @@ import org.jclouds.googlecomputeengine.domain.Operation;
import org.jclouds.location.suppliers.ImplicitLocationSupplier; import org.jclouds.location.suppliers.ImplicitLocationSupplier;
import org.jclouds.location.suppliers.implicit.FirstZone; import org.jclouds.location.suppliers.implicit.FirstZone;
import com.google.common.base.Optional;
import com.google.common.base.Function; import com.google.common.base.Function;
import com.google.common.base.Functions; import com.google.common.base.Functions;
import com.google.common.base.Predicate; import com.google.common.base.Predicate;
@ -134,7 +135,7 @@ public final class GoogleComputeEngineServiceContextModule
bind(FirewallTagNamingConvention.Factory.class).in(Scopes.SINGLETON); bind(FirewallTagNamingConvention.Factory.class).in(Scopes.SINGLETON);
bind(new TypeLiteral<CacheLoader<URI, Image>>() { bind(new TypeLiteral<CacheLoader<URI, Optional<Image>>>() {
}).to(DiskURIToImage.class); }).to(DiskURIToImage.class);
bindHttpApi(binder(), Resources.class); bindHttpApi(binder(), Resources.class);
@ -202,8 +203,8 @@ public final class GoogleComputeEngineServiceContextModule
@Provides @Provides
@Singleton @Singleton
protected LoadingCache<URI, Image> diskURIToImageMap( protected LoadingCache<URI, Optional<Image>> diskURIToImageMap(
CacheLoader<URI, Image> in) { CacheLoader<URI, Optional<Image>> in) {
return CacheBuilder.newBuilder().build(in); return CacheBuilder.newBuilder().build(in);
} }

View File

@ -17,6 +17,7 @@
package org.jclouds.googlecomputeengine.compute.functions; package org.jclouds.googlecomputeengine.compute.functions;
import com.google.common.base.Function; import com.google.common.base.Function;
import com.google.common.base.Optional;
import com.google.common.base.Splitter; import com.google.common.base.Splitter;
import com.google.common.base.Supplier; import com.google.common.base.Supplier;
import com.google.common.cache.LoadingCache; import com.google.common.cache.LoadingCache;
@ -44,13 +45,13 @@ public final class InstanceToNodeMetadata implements Function<Instance, NodeMeta
private final Map<Instance.Status, NodeMetadata.Status> toPortableNodeStatus; private final Map<Instance.Status, NodeMetadata.Status> toPortableNodeStatus;
private final GroupNamingConvention nodeNamingConvention; private final GroupNamingConvention nodeNamingConvention;
private final LoadingCache<URI, Image> diskURIToImage; private final LoadingCache<URI, Optional<Image>> diskURIToImage;
private final Supplier<Map<URI, Hardware>> hardwares; private final Supplier<Map<URI, Hardware>> hardwares;
private final Supplier<Map<URI, Location>> locationsByUri; private final Supplier<Map<URI, Location>> locationsByUri;
@Inject InstanceToNodeMetadata(Map<Instance.Status, NodeMetadata.Status> toPortableNodeStatus, @Inject InstanceToNodeMetadata(Map<Instance.Status, NodeMetadata.Status> toPortableNodeStatus,
GroupNamingConvention.Factory namingConvention, GroupNamingConvention.Factory namingConvention,
LoadingCache<URI, Image> diskURIToImage, LoadingCache<URI, Optional<Image>> diskURIToImage,
@Memoized Supplier<Map<URI, Hardware>> hardwares, @Memoized Supplier<Map<URI, Hardware>> hardwares,
@Memoized Supplier<Map<URI, Location>> locationsByUri) { @Memoized Supplier<Map<URI, Location>> locationsByUri) {
this.toPortableNodeStatus = toPortableNodeStatus; this.toPortableNodeStatus = toPortableNodeStatus;
@ -74,7 +75,9 @@ public final class InstanceToNodeMetadata implements Function<Instance, NodeMeta
// //
// Note: This will be present if we created the node. In the future we could choose to make diskToSourceImage // Note: This will be present if we created the node. In the future we could choose to make diskToSourceImage
// a loading cache. That would be more expensive, but could ensure this isn't null. // a loading cache. That would be more expensive, but could ensure this isn't null.
Image image = diskURIToImage.getUnchecked(input.disks().get(0).source());
URI diskSource = input.disks().get(0).source();
Optional<Image> image = diskURIToImage.getUnchecked(diskSource);
Hardware hardware; Hardware hardware;
if (isCustomMachineTypeURI(input.machineType())) { if (isCustomMachineTypeURI(input.machineType())) {
@ -89,7 +92,7 @@ public final class InstanceToNodeMetadata implements Function<Instance, NodeMeta
.providerId(input.id()) .providerId(input.id())
.hostname(input.name()) .hostname(input.name())
.location(zone) .location(zone)
.imageId(image != null ? image.selfLink().toString() : null) .imageId(image.isPresent() ? image.get().selfLink().toString() : null)
.hardware(hardware) .hardware(hardware)
.status(input.status() != null ? toPortableNodeStatus.get(input.status()) : Status.UNRECOGNIZED) .status(input.status() != null ? toPortableNodeStatus.get(input.status()) : Status.UNRECOGNIZED)
.tags(input.tags().items()) .tags(input.tags().items())

View File

@ -22,6 +22,7 @@ import javax.inject.Singleton;
import java.net.URI; import java.net.URI;
import java.util.concurrent.ExecutionException; import java.util.concurrent.ExecutionException;
import com.google.common.base.Optional;
import com.google.common.cache.CacheLoader; import com.google.common.cache.CacheLoader;
import org.jclouds.googlecomputeengine.compute.functions.Resources; import org.jclouds.googlecomputeengine.compute.functions.Resources;
import org.jclouds.googlecomputeengine.domain.Disk; import org.jclouds.googlecomputeengine.domain.Disk;
@ -30,7 +31,7 @@ import org.jclouds.logging.Logger;
@Singleton @Singleton
public class DiskURIToImage extends CacheLoader<URI, Image> { public class DiskURIToImage extends CacheLoader<URI, Optional<Image>> {
@Resource @Resource
protected Logger logger = Logger.NULL; protected Logger logger = Logger.NULL;
@ -42,10 +43,12 @@ public class DiskURIToImage extends CacheLoader<URI, Image> {
} }
@Override @Override
public Image load(URI key) throws ExecutionException { public Optional<Image> load(URI key) throws ExecutionException {
try { try {
Disk disk = resources.disk(key); Disk disk = resources.disk(key);
return resources.image(disk.sourceImage()); URI sourceImage = disk.sourceImage();
Image image = sourceImage != null ? resources.image(sourceImage) : null;
return Optional.fromNullable(image);
} catch (Exception e) { } catch (Exception e) {
throw new ExecutionException(message(key, e), e); throw new ExecutionException(message(key, e), e);
} }

View File

@ -148,6 +148,26 @@ public class GoogleComputeEngineServiceMockTest extends BaseGoogleComputeEngineA
assertSent(server, "GET", "/projects/party/aggregated/machineTypes"); assertSent(server, "GET", "/projects/party/aggregated/machineTypes");
} }
public void listNodesWithSnapshotSource() throws Exception {
server.enqueue(aggregatedListWithInstanceNetworkAndStatus("test-0", "test-network", RUNNING));
server.enqueue(singleRegionSingleZoneResponse());
server.enqueue(jsonResponse("/disk_get_with_source_snapshot.json"));
server.enqueue(jsonResponse("/aggregated_machinetype_list.json"));
Set<? extends ComputeMetadata> nodes = computeService().listNodes();
assertEquals(nodes.size(), 1);
NodeMetadata node = (NodeMetadata) nodes.iterator().next();
String imageId = node.getImageId();
assertEquals(imageId, null);
assertSent(server, "GET", "/projects/party/aggregated/instances");
assertSent(server, "GET", "/projects/party/regions");
assertSent(server, "GET", "/projects/party/zones/us-central1-a/disks/test");
assertSent(server, "GET", "/projects/party/aggregated/machineTypes");
}
public void createNodeWhenFirewallDoesNotExist() throws Exception { public void createNodeWhenFirewallDoesNotExist() throws Exception {
server.enqueue(singleRegionSingleZoneResponse()); server.enqueue(singleRegionSingleZoneResponse());
server.enqueue(jsonResponse("/image_list.json")); server.enqueue(jsonResponse("/image_list.json"));

View File

@ -18,6 +18,7 @@ package org.jclouds.googlecomputeengine.compute.functions;
import com.google.common.base.Function; import com.google.common.base.Function;
import com.google.common.base.Functions; import com.google.common.base.Functions;
import com.google.common.base.Optional;
import com.google.common.base.Predicate; import com.google.common.base.Predicate;
import com.google.common.base.Supplier; import com.google.common.base.Supplier;
import com.google.common.base.Suppliers; import com.google.common.base.Suppliers;
@ -176,8 +177,8 @@ public class InstanceToNodeMetadataTest {
} }
}; };
Map<URI, Image> imageMap = ImmutableMap.of(instance.disks().get(0).source(), Map<URI, Optional<Image>> imageMap = ImmutableMap.of(instance.disks().get(0).source(),
new ParseImageTest().expected()); Optional.of(new ParseImageTest().expected()));
return new InstanceToNodeMetadata( return new InstanceToNodeMetadata(
ImmutableMap.<Instance.Status, NodeMetadata.Status>builder() ImmutableMap.<Instance.Status, NodeMetadata.Status>builder()

View File

@ -0,0 +1,12 @@
{
"kind": "compute#disk",
"id": "13050421646334304115",
"creationTimestamp": "2012-11-25T01:38:48.306",
"selfLink": "https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/disks/test",
"name": "test",
"sizeGb": "1",
"zone": "https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a",
"status": "READY",
"type": "https://www.googleapis.com/compute/v1/projects/studied-point-720/zones/us-central1-a/diskTypes/pd-standard",
"sourceSnapshot": "https://www.googleapis.com/compute/v1/projects/party/global/snapshots/snapshot"
}