Repository: jclouds-labs-google
Updated Branches:
  refs/heads/master f41d49cea -> e50999ec5


Added TargetInstanceApi


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

Branch: refs/heads/master
Commit: e50999ec52f0a4dbf4b647a276fc2c6485420355
Parents: f41d49c
Author: Daniel Broudy <[email protected]>
Authored: Thu Nov 20 19:02:14 2014 -0800
Committer: Adrian Cole <[email protected]>
Committed: Wed Nov 26 17:44:46 2014 -0800

----------------------------------------------------------------------
 .../GoogleComputeEngineApi.java                 |   6 +
 .../domain/NewTargetInstance.java               |  72 +++++++++++
 .../domain/TargetInstance.java                  |  48 +++++++
 .../features/AggregatedListApi.java             |  51 ++++++++
 .../features/TargetInstanceApi.java             | 129 +++++++++++++++++++
 .../features/AggregatedListApiLiveTest.java     |  18 +++
 .../features/AggregatedListApiMockTest.java     |  20 +++
 .../features/TargetInstanceApiLiveTest.java     |  77 +++++++++++
 .../features/TargetInstanceApiMockTest.java     | 101 +++++++++++++++
 .../parse/ParseTargetInstanceListTest.java      |  60 +++++++++
 .../parse/ParseTargetInstanceTest.java          |  51 ++++++++
 .../aggregated_target_instance_list.json        | 128 ++++++++++++++++++
 .../aggregated_target_instance_list_empty.json  |  55 ++++++++
 .../src/test/resources/target_instance_get.json |  11 ++
 .../test/resources/target_instance_insert.json  |   6 +
 .../test/resources/target_instance_list.json    |  30 +++++
 16 files changed, 863 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/GoogleComputeEngineApi.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/GoogleComputeEngineApi.java
 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/GoogleComputeEngineApi.java
index 8a6e36c..14a3961 100644
--- 
a/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/GoogleComputeEngineApi.java
+++ 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/GoogleComputeEngineApi.java
@@ -39,6 +39,7 @@ import org.jclouds.googlecomputeengine.features.ProjectApi;
 import org.jclouds.googlecomputeengine.features.RegionApi;
 import org.jclouds.googlecomputeengine.features.RouteApi;
 import org.jclouds.googlecomputeengine.features.SnapshotApi;
+import org.jclouds.googlecomputeengine.features.TargetInstanceApi;
 import org.jclouds.googlecomputeengine.features.TargetPoolApi;
 import org.jclouds.googlecomputeengine.features.TargetHttpProxyApi;
 import org.jclouds.googlecomputeengine.features.UrlMapApi;
@@ -137,6 +138,11 @@ public interface GoogleComputeEngineApi extends Closeable {
 
    @Delegate
    @Endpoint(CurrentProject.class)
+   @Path("/zones/{zone}")
+   TargetInstanceApi targetInstancesInZone(@PathParam("zone") String zone);
+
+   @Delegate
+   @Endpoint(CurrentProject.class)
    @Path("/regions/{region}")
    TargetPoolApi targetPoolsInRegion(@PathParam("region") String region);
 

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/domain/NewTargetInstance.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/domain/NewTargetInstance.java
 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/domain/NewTargetInstance.java
new file mode 100644
index 0000000..478bfce
--- /dev/null
+++ 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/domain/NewTargetInstance.java
@@ -0,0 +1,72 @@
+/*
+ * 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.googlecomputeengine.domain;
+
+import java.net.URI;
+
+import org.jclouds.javax.annotation.Nullable;
+import org.jclouds.json.SerializedNames;
+
+import com.google.auto.value.AutoValue;
+
+@AutoValue
+public abstract class NewTargetInstance {
+
+   public abstract String name();
+   @Nullable public abstract String description();
+   @Nullable public abstract String natPolicy();
+   @Nullable public abstract URI instance();
+
+   @SerializedNames({"name", "description", "natPolicy", "instance"})
+   static NewTargetInstance create(String name, String description, String 
natPolicy, URI instance){
+      return new AutoValue_NewTargetInstance(name, description, natPolicy, 
instance);
+   }
+
+   NewTargetInstance() {
+   }
+
+   public static class Builder {
+      private String name;
+      private String description;
+      private String natPolicy;
+      private URI instance;
+
+      public Builder name(String name) {
+         this.name = name;
+         return this;
+      }
+
+      public Builder description(String description) {
+         this.description = description;
+         return this;
+      }
+
+      public Builder natPolicy(String natPolicy) {
+         this.natPolicy = natPolicy;
+         return this;
+      }
+
+      public Builder instance(URI instance) {
+         this.instance = instance;
+         return this;
+      }
+
+      public NewTargetInstance build() {
+         return NewTargetInstance.create(name, description, natPolicy, 
instance);
+      }
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/domain/TargetInstance.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/domain/TargetInstance.java
 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/domain/TargetInstance.java
new file mode 100644
index 0000000..656bc8f
--- /dev/null
+++ 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/domain/TargetInstance.java
@@ -0,0 +1,48 @@
+/*
+ * 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.googlecomputeengine.domain;
+
+
+import java.net.URI;
+
+import org.jclouds.javax.annotation.Nullable;
+import org.jclouds.json.SerializedNames;
+
+import com.google.auto.value.AutoValue;
+
+@AutoValue
+public abstract class TargetInstance {
+
+   public abstract String creationTimestamp();
+   public abstract String name();
+   @Nullable public abstract String description();
+   public abstract URI zone();
+   public abstract String natPolicy();
+   @Nullable public abstract URI instance();
+   public abstract URI selfLink();
+
+   @SerializedNames({"creationTimestamp", "name", "description", "zone",
+      "natPolicy", "instance", "selfLink"})
+   public static TargetInstance create(String creationTimestamp, String name,
+         String description, URI zone, String natPolicy, URI instance, URI 
selfLink){
+      return new AutoValue_TargetInstance(creationTimestamp, name, 
description, zone,
+            natPolicy, instance, selfLink);
+   }
+
+   TargetInstance(){
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/AggregatedListApi.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/AggregatedListApi.java
 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/AggregatedListApi.java
index de12f51..55ff6b2 100644
--- 
a/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/AggregatedListApi.java
+++ 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/AggregatedListApi.java
@@ -36,6 +36,7 @@ import org.jclouds.googlecomputeengine.domain.ForwardingRule;
 import org.jclouds.googlecomputeengine.domain.Instance;
 import org.jclouds.googlecomputeengine.domain.MachineType;
 import org.jclouds.googlecomputeengine.domain.Operation;
+import org.jclouds.googlecomputeengine.domain.TargetInstance;
 import org.jclouds.googlecomputeengine.internal.BaseToIteratorOfListPage;
 import org.jclouds.googlecomputeengine.options.ListOptions;
 import org.jclouds.javax.annotation.Nullable;
@@ -396,4 +397,54 @@ public interface AggregatedListApi {
          };
       }
    }
+
+   /**
+    * Retrieves the list of TargetInstance resources available to the
+    * specified project. By default the list as a maximum size of 100, if no
+    * options are provided or ListOptions#getMaxResults() has not been set.
+    *
+    * @param pageToken
+    *           marks the beginning of the next list page
+    * @param listOptions
+    *           listing options
+    * @return a page of the list
+    */
+   @Named("TargetInstances:aggregatedList")
+   @GET
+   @Path("/targetInstances")
+   ListPage<TargetInstance> pageOfTargetInstances(@Nullable 
@QueryParam("pageToken") String pageToken,
+         ListOptions listOptions);
+
+   /** @see #pageOfTargetInstances(String, ListOptions) */
+   @Named("TargetInstances:aggregatedList")
+   @GET
+   @Path("/targetInstances")
+   @Transform(TargetInstancePages.class)
+   Iterator<ListPage<TargetInstance>> targetInstances();
+
+   /** @see #pageOfTargetInstances(String, ListOptions) */
+   @Named("TargetInstances:aggregatedList")
+   @GET
+   @Path("/targetInstances")
+   @Transform(TargetInstancePages.class)
+   Iterator<ListPage<TargetInstance>> targetInstances(ListOptions options);
+
+   static final class TargetInstancePages extends 
BaseToIteratorOfListPage<TargetInstance, TargetInstancePages> {
+      private final GoogleComputeEngineApi api;
+
+      @Inject
+      TargetInstancePages(GoogleComputeEngineApi api) {
+         this.api = api;
+      }
+
+      @Override
+      protected Function<String, ListPage<TargetInstance>> fetchNextPage(final 
ListOptions options) {
+            return new Function<String, ListPage<TargetInstance>>() {
+               @Override
+               public ListPage<TargetInstance> apply(String pageToken) {
+                  return api.aggregatedList().pageOfTargetInstances(pageToken, 
options);
+               }
+            };
+      }
+   }
 }

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/TargetInstanceApi.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/TargetInstanceApi.java
 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/TargetInstanceApi.java
new file mode 100644
index 0000000..6d2c3cc
--- /dev/null
+++ 
b/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/features/TargetInstanceApi.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.googlecomputeengine.features;
+
+import static javax.ws.rs.core.MediaType.APPLICATION_JSON;
+
+import java.util.Iterator;
+
+import javax.inject.Inject;
+import javax.inject.Named;
+import javax.ws.rs.Consumes;
+import javax.ws.rs.DELETE;
+import javax.ws.rs.GET;
+import javax.ws.rs.POST;
+import javax.ws.rs.Path;
+import javax.ws.rs.PathParam;
+import javax.ws.rs.Produces;
+import javax.ws.rs.QueryParam;
+
+import org.jclouds.Fallbacks.NullOnNotFoundOr404;
+import org.jclouds.googlecloud.domain.ListPage;
+import org.jclouds.googlecomputeengine.GoogleComputeEngineApi;
+import org.jclouds.googlecomputeengine.domain.NewTargetInstance;
+import org.jclouds.googlecomputeengine.domain.Operation;
+import org.jclouds.googlecomputeengine.domain.TargetInstance;
+import 
org.jclouds.googlecomputeengine.internal.BaseCallerArg0ToIteratorOfListPage;
+import org.jclouds.googlecomputeengine.options.ListOptions;
+import org.jclouds.javax.annotation.Nullable;
+import org.jclouds.oauth.v2.filters.OAuthFilter;
+import org.jclouds.rest.annotations.BinderParam;
+import org.jclouds.rest.annotations.Fallback;
+import org.jclouds.rest.annotations.RequestFilters;
+import org.jclouds.rest.annotations.SkipEncoding;
+import org.jclouds.rest.annotations.Transform;
+import org.jclouds.rest.binders.BindToJsonPayload;
+
+import com.google.common.base.Function;
+
+@SkipEncoding({'/', '='})
+@RequestFilters(OAuthFilter.class)
+@Path("/targetInstances")
+@Consumes(APPLICATION_JSON)
+public interface TargetInstanceApi {
+
+   /** Returns a targetInstance by name or null if not found. */
+   @Named("TargetInstances:get")
+   @GET
+   @Path("/{targetInstance}")
+   @Fallback(NullOnNotFoundOr404.class)
+   @Nullable
+   TargetInstance get(@PathParam("targetInstance") String targetInstance);
+
+   /**
+    * Creates a instance resource in the specified project using the data 
included in the request.
+    *
+    * @param template the instance template
+    * @return an Operation resource. To check on the status of an operation, 
poll the Operations resource returned to
+    *         you, and look for the status field.
+    */
+   @Named("TargetInstances:insert")
+   @POST
+   @Produces(APPLICATION_JSON)
+   Operation create(@BinderParam(BindToJsonPayload.class) NewTargetInstance 
targetInstance);
+
+   /** Deletes a targetInstance by name and returns the operation in progress, 
or null if not found. */
+   @Named("TargetInstances:delete")
+   @DELETE
+   @Path("/{targetInstance}")
+   @Fallback(NullOnNotFoundOr404.class)
+   @Nullable
+   Operation delete(@PathParam("targetInstance") String targetInstance);
+
+   /**
+    * Retrieves the list of targetInstance resources available to the 
specified project.
+    * By default the list as a maximum size of 100, if no options are provided 
or ListOptions#getMaxResults() has not
+    * been set.
+    *
+    * @param pageToken   marks the beginning of the next list page
+    * @param listOptions listing options
+    * @return a page of the list
+    */
+   @Named("TargetInstances:list")
+   @GET
+   ListPage<TargetInstance> listPage(@Nullable @QueryParam("pageToken") String 
pageToken, ListOptions listOptions);
+
+   /** @see #listPage(String, ListOptions) */
+   @Named("TargetInstances:list")
+   @GET
+   @Transform(TargetInstancePages.class)
+   Iterator<ListPage<TargetInstance>> list();
+
+   /** @see #listPage(String, ListOptions) */
+   @Named("TargetInstances:list")
+   @GET
+   @Transform(TargetInstancePages.class)
+   Iterator<ListPage<TargetInstance>> list(ListOptions options);
+
+   static final class TargetInstancePages extends 
BaseCallerArg0ToIteratorOfListPage<TargetInstance, TargetInstancePages> {
+
+      private final GoogleComputeEngineApi api;
+
+      @Inject TargetInstancePages(GoogleComputeEngineApi api) {
+         this.api = api;
+      }
+
+      @Override
+      protected Function<String, ListPage<TargetInstance>> fetchNextPage(final 
String zoneName, final ListOptions options) {
+         return new Function<String, ListPage<TargetInstance>>() {
+            @Override public ListPage<TargetInstance> apply(String pageToken) {
+               return api.targetInstancesInZone(zoneName).listPage(pageToken, 
options);
+            }
+         };
+      }
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiLiveTest.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiLiveTest.java
 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiLiveTest.java
index e119872..c1e2f62 100644
--- 
a/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiLiveTest.java
+++ 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiLiveTest.java
@@ -30,6 +30,7 @@ import org.jclouds.googlecomputeengine.domain.DiskType;
 import org.jclouds.googlecomputeengine.domain.ForwardingRule;
 import org.jclouds.googlecomputeengine.domain.MachineType;
 import org.jclouds.googlecomputeengine.domain.Operation;
+import org.jclouds.googlecomputeengine.domain.TargetInstance;
 import 
org.jclouds.googlecomputeengine.internal.BaseGoogleComputeEngineApiLiveTest;
 import org.testng.SkipException;
 import org.testng.annotations.Test;
@@ -129,4 +130,21 @@ public class AggregatedListApiLiveTest extends 
BaseGoogleComputeEngineApiLiveTes
       }
       assertEquals(count, 2);
    }
+
+   public void targetInstances() {
+      Iterator<ListPage<TargetInstance>> pageIterator = 
api().targetInstances(maxResults(1));
+      // make sure that in spite of having only one result per page we get at
+      // least two results
+      int count = 0;
+      for (; count < 2 && pageIterator.hasNext();) {
+         ListPage<TargetInstance> result = pageIterator.next();
+         if (!result.isEmpty()) {
+            count++;
+         }
+      }
+      if (count < 2) {
+         throw new SkipException("Not enough target instances");
+      }
+      assertEquals(count, 2);
+   }
 }

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiMockTest.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiMockTest.java
 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiMockTest.java
index ea39619..a02ec07 100644
--- 
a/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiMockTest.java
+++ 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/AggregatedListApiMockTest.java
@@ -164,4 +164,24 @@ public class AggregatedListApiMockTest extends 
BaseGoogleComputeEngineApiMockTes
 
       assertSent(server, "GET", "/projects/party/aggregated/forwardingRules");
    }
+
+   public void targetInstances() throws Exception {
+      server.enqueue(jsonResponse("/aggregated_target_instance_list.json"));
+
+      AggregatedListApi aggregatedList = api().aggregatedList();
+
+      assertTrue(aggregatedList.targetInstances().hasNext());
+
+      assertSent(server, "GET", "/projects/party/aggregated/targetInstances");
+   }
+
+   public void targetInstancesResponseIs4xx() throws Exception {
+      
server.enqueue(jsonResponse("/aggregated_target_instance_list_empty.json"));
+
+      AggregatedListApi aggregatedList = api().aggregatedList();
+
+      assertFalse(aggregatedList.targetInstances().hasNext());
+
+      assertSent(server, "GET", "/projects/party/aggregated/targetInstances");
+   }
 }

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/TargetInstanceApiLiveTest.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/TargetInstanceApiLiveTest.java
 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/TargetInstanceApiLiveTest.java
new file mode 100644
index 0000000..3b25b40
--- /dev/null
+++ 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/TargetInstanceApiLiveTest.java
@@ -0,0 +1,77 @@
+/*
+ * 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.googlecomputeengine.features;
+
+import static 
org.jclouds.googlecomputeengine.options.ListOptions.Builder.filter;
+import static org.testng.Assert.assertEquals;
+import static org.testng.Assert.assertNotNull;
+
+import org.jclouds.googlecloud.domain.ListPage;
+import org.jclouds.googlecomputeengine.domain.NewTargetInstance;
+import org.jclouds.googlecomputeengine.domain.TargetInstance;
+import 
org.jclouds.googlecomputeengine.internal.BaseGoogleComputeEngineApiLiveTest;
+import org.testng.annotations.Test;
+
+import com.google.common.collect.Iterables;
+
+
+public class TargetInstanceApiLiveTest extends 
BaseGoogleComputeEngineApiLiveTest {
+
+   public static final String TARGET_INSTANCE_NAME = "test-target-instance-1";
+
+   @Test(groups = "live")
+   public void testInsertTargetInstance(){
+
+      NewTargetInstance newTargetInstance = new NewTargetInstance.Builder()
+         .name(TARGET_INSTANCE_NAME)
+         .description("A test Target Instance")
+         .build();
+
+      
assertOperationDoneSuccessfully(api.targetInstancesInZone(DEFAULT_ZONE_NAME).create(newTargetInstance));
+   }
+
+   @Test(groups = "live", dependsOnMethods = "testInsertTargetInstance")
+   public void testGetTargetInstance(){
+      TargetInstance targetInstance = 
api.targetInstancesInZone(DEFAULT_ZONE_NAME).get(TARGET_INSTANCE_NAME);
+
+      assertNotNull(targetInstance);
+      assertEquals(targetInstance.name(), TARGET_INSTANCE_NAME);
+      assertEquals(targetInstance.description(), "A test Target Instance");
+      assertEquals(targetInstance.zone(), getZoneUrl(DEFAULT_ZONE_NAME));
+   }
+
+   @Test(groups = "live", dependsOnMethods = "testInsertTargetInstance", 
alwaysRun = true)
+   public void testListTargetInstance(){
+      ListPage<TargetInstance> targetInstances = 
api.targetInstancesInZone(DEFAULT_ZONE_NAME)
+            .list(filter("name eq " + TARGET_INSTANCE_NAME)).next();
+
+      assertEquals(targetInstances.size(), 1);
+      assertTargetInstanceEquals(Iterables.getOnlyElement(targetInstances));
+   }
+
+   @Test(groups = "live", dependsOnMethods = {"testListTargetInstance", 
"testGetTargetInstance"}, alwaysRun = true)
+   public void testDeleteTargetInstance(){
+      
assertOperationDoneSuccessfully(api.targetInstancesInZone(DEFAULT_ZONE_NAME).delete(TARGET_INSTANCE_NAME));
+   }
+
+   private void assertTargetInstanceEquals(TargetInstance targetInstance){
+      assertNotNull(targetInstance);
+      assertEquals(targetInstance.name(), TARGET_INSTANCE_NAME);
+      assertEquals(targetInstance.description(), "A test Target Instance");
+      assertEquals(targetInstance.zone(), getZoneUrl(DEFAULT_ZONE_NAME));
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/TargetInstanceApiMockTest.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/TargetInstanceApiMockTest.java
 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/TargetInstanceApiMockTest.java
new file mode 100644
index 0000000..2bca642
--- /dev/null
+++ 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/features/TargetInstanceApiMockTest.java
@@ -0,0 +1,101 @@
+/*
+ * 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.googlecomputeengine.features;
+
+import static org.testng.Assert.assertEquals;
+import static org.testng.Assert.assertFalse;
+import static org.testng.Assert.assertNull;
+
+import java.net.URI;
+
+import org.jclouds.googlecomputeengine.domain.NewTargetInstance;
+import 
org.jclouds.googlecomputeengine.internal.BaseGoogleComputeEngineApiMockTest;
+import org.jclouds.googlecomputeengine.parse.ParseOperationTest;
+import org.jclouds.googlecomputeengine.parse.ParseTargetInstanceListTest;
+import org.jclouds.googlecomputeengine.parse.ParseTargetInstanceTest;
+import org.testng.annotations.Test;
+
+@Test(groups = "unit", testName = "TargetInstanceApiMockTest", singleThreaded 
= true)
+public class TargetInstanceApiMockTest extends 
BaseGoogleComputeEngineApiMockTest {
+
+   public static String TARGET_INSTANCE_NAME = "target-instance-1";
+
+   public void get() throws Exception {
+      server.enqueue(jsonResponse("/target_instance_get.json"));
+
+      assertEquals(targetInstanceApi().get(TARGET_INSTANCE_NAME),
+            new ParseTargetInstanceTest().expected(url("/projects")));
+      assertSent(server, "GET", 
"/projects/party/zones/us-central1-a/targetInstances/" + TARGET_INSTANCE_NAME);
+   }
+
+   public void get_4xx() throws Exception {
+      server.enqueue(response404());
+
+      assertNull(targetInstanceApi().get(TARGET_INSTANCE_NAME));
+      assertSent(server, "GET", 
"/projects/party/zones/us-central1-a/targetInstances/" + TARGET_INSTANCE_NAME);
+   }
+
+   public void insert() throws Exception {
+      server.enqueue(jsonResponse("/operation.json"));
+
+      NewTargetInstance options = new NewTargetInstance.Builder()
+         .name("test-target-instance")
+         .description("This is a test")
+         .natPolicy("NO_NAT")
+         
.instance(URI.create(url("/projects/party/zones/us-central1-a/instances/instance-1")))
+         .build();
+
+      assertEquals(targetInstanceApi().create(options),
+            new ParseOperationTest().expected(url("/projects")));
+
+      assertSent(server, "POST", 
"/projects/party/zones/us-central1-a/targetInstances",
+            stringFromResource("/target_instance_insert.json"));
+   }
+
+   public void testDeleteImageResponseIs2xx()  throws Exception {
+      server.enqueue(jsonResponse("/operation.json"));
+
+      assertEquals(targetInstanceApi().delete(TARGET_INSTANCE_NAME),
+            new ParseOperationTest().expected(url("/projects")));
+      assertSent(server, "DELETE", 
"/projects/party/zones/us-central1-a/targetInstances/" + TARGET_INSTANCE_NAME);
+   }
+
+   public void delete() throws Exception {
+      server.enqueue(response404());
+
+      assertNull(targetInstanceApi().delete(TARGET_INSTANCE_NAME));
+      assertSent(server, "DELETE", 
"/projects/party/zones/us-central1-a/targetInstances/" + TARGET_INSTANCE_NAME);
+   }
+
+   public void list() throws InterruptedException {
+      server.enqueue(jsonResponse("/target_instance_list.json"));
+
+      assertEquals(targetInstanceApi().list().next(), new 
ParseTargetInstanceListTest().expected(url("/projects")));
+      assertSent(server, "GET", 
"/projects/party/zones/us-central1-a/targetInstances");
+   }
+
+   public void listEmpty() throws InterruptedException {
+      server.enqueue(jsonResponse("/list_empty.json"));
+
+      assertFalse(targetInstanceApi().list().hasNext());
+      assertSent(server, "GET", 
"/projects/party/zones/us-central1-a/targetInstances");
+   }
+
+   TargetInstanceApi targetInstanceApi() {
+      return api().targetInstancesInZone("us-central1-a");
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/parse/ParseTargetInstanceListTest.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/parse/ParseTargetInstanceListTest.java
 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/parse/ParseTargetInstanceListTest.java
new file mode 100644
index 0000000..4af9d4d
--- /dev/null
+++ 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/parse/ParseTargetInstanceListTest.java
@@ -0,0 +1,60 @@
+/*
+ * 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.googlecomputeengine.parse;
+
+import static javax.ws.rs.core.MediaType.APPLICATION_JSON;
+
+import java.net.URI;
+
+import javax.ws.rs.Consumes;
+
+import org.jclouds.googlecloud.domain.ForwardingListPage;
+import org.jclouds.googlecloud.domain.ListPage;
+import org.jclouds.googlecomputeengine.domain.TargetInstance;
+import 
org.jclouds.googlecomputeengine.internal.BaseGoogleComputeEngineParseTest;
+import org.testng.annotations.Test;
+
+import com.google.common.collect.ImmutableList;
+
+@Test(groups = "unit", testName = "ParseTargetInstanceListTest")
+public class ParseTargetInstanceListTest extends 
BaseGoogleComputeEngineParseTest<ListPage<TargetInstance>> {
+
+   @Override
+   public String resource() {
+      return "/target_instance_list.json";
+   }
+
+   @Override @Consumes(APPLICATION_JSON)
+   public ListPage<TargetInstance> expected() {
+      return expected(BASE_URL);
+   }
+
+   public ListPage<TargetInstance> expected(String baseURL){
+      return ForwardingListPage.create( //
+            ImmutableList.of(new ParseTargetInstanceTest().expected(baseURL),
+                  TargetInstance.create("2014-11-20T17:35:17.268-08:00", // 
creationTimestamp
+                        "target-instance-2", // name
+                        null, // description
+                        URI.create(baseURL + "/party/zones/us-central1-a"), // 
zone
+                        "NO_NAT", // natPolicy
+                        URI.create(baseURL + 
"/party/zones/us-central1-a/instances/test-3"), // instance
+                        URI.create(baseURL + 
"/party/zones/us-central1-a/targetInstances/target-instance-2") // selfLink
+                        )), // items
+            null // nextPageToken
+      );
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/parse/ParseTargetInstanceTest.java
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/parse/ParseTargetInstanceTest.java
 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/parse/ParseTargetInstanceTest.java
new file mode 100644
index 0000000..deae9f4
--- /dev/null
+++ 
b/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/parse/ParseTargetInstanceTest.java
@@ -0,0 +1,51 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jclouds.googlecomputeengine.parse;
+
+import static javax.ws.rs.core.MediaType.APPLICATION_JSON;
+
+import java.net.URI;
+
+import javax.ws.rs.Consumes;
+
+import org.jclouds.googlecomputeengine.domain.TargetInstance;
+import 
org.jclouds.googlecomputeengine.internal.BaseGoogleComputeEngineParseTest;
+import org.testng.annotations.Test;
+
+@Test(groups = "unit", testName = "ParseTargetInstanceTest")
+public class ParseTargetInstanceTest extends 
BaseGoogleComputeEngineParseTest<TargetInstance> {
+
+   @Override
+   public String resource() {
+      return "/target_instance_get.json";
+   }
+
+   @Override @Consumes(APPLICATION_JSON)
+   public TargetInstance expected() {
+      return expected(BASE_URL);
+   }
+
+   public TargetInstance expected(String baseUrl) {
+      return TargetInstance.create("2014-07-18T09:47:30.826-07:00", // 
creationTimestamp
+            "target-instance-1", // name
+            "A pretty cool target instance", // description
+            URI.create(baseUrl + "/party/zones/us-central1-a"), // zone
+            "NO_NAT", // natPolicy
+            URI.create(baseUrl + 
"/party/zones/us-central1-a/instances/test-0"), // instance
+            URI.create(baseUrl + 
"/party/zones/us-central1-a/targetInstances/target-instance-1")); //selfLink
+   }
+}

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/resources/aggregated_target_instance_list.json
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/resources/aggregated_target_instance_list.json 
b/google-compute-engine/src/test/resources/aggregated_target_instance_list.json
new file mode 100644
index 0000000..e1e56b9
--- /dev/null
+++ 
b/google-compute-engine/src/test/resources/aggregated_target_instance_list.json
@@ -0,0 +1,128 @@
+{
+ "kind": "compute#targetInstanceAggregatedList",
+ "selfLink": 
"https://www.googleapis.com/compute/v1/projects/party/aggregated/targetInstances";,
+ "id": "projects/party/aggregated/targetInstances",
+ "items": {
+  "zones/asia-east1-a": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'zones/asia-east1-a' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "zones/asia-east1-a"
+     }
+    ]
+   }
+  },
+  "zones/asia-east1-b": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'zones/asia-east1-b' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "zones/asia-east1-b"
+     }
+    ]
+   }
+  },
+  "zones/asia-east1-c": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'zones/asia-east1-c' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "zones/asia-east1-c"
+     }
+    ]
+   }
+  },
+  "zones/europe-west1-a": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'zones/europe-west1-a' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "zones/europe-west1-a"
+     }
+    ]
+   }
+  },
+  "zones/europe-west1-b": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'zones/europe-west1-b' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "zones/europe-west1-b"
+     }
+    ]
+   }
+  },
+  "zones/europe-west1-c": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'zones/europe-west1-c' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "zones/europe-west1-c"
+     }
+    ]
+   }
+  },
+  "zones/us-central1-a": {
+   "targetInstances": [
+    {
+
+     "kind": "compute#targetInstance",
+     "id": "3191835352771895826",
+     "creationTimestamp": "2014-11-24T10:42:45.135-08:00",
+     "name": "test-target-instance",
+     "zone": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a";,
+     "natPolicy": "NO_NAT",
+     "instance": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/instances/instance-1";,
+     "selfLink": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/targetInstances/test-target-instance";
+    },
+    {
+
+     "kind": "compute#targetInstance",
+     "id": "7362436693678237415",
+     "creationTimestamp": "2014-11-20T17:35:17.268-08:00",
+     "name": "target-instance-1",
+     "zone": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a";,
+     "natPolicy": "NO_NAT",
+     "selfLink": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/targetInstances/target-instance-1";
+    }
+   ]
+  },
+  "zones/us-central1-b": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'zones/us-central1-b' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "zones/us-central1-b"
+     }
+    ]
+   }
+  },
+  "zones/us-central1-f": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'zones/us-central1-f' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "zones/us-central1-f"
+     }
+    ]
+   }
+  }
+ }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/resources/aggregated_target_instance_list_empty.json
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/resources/aggregated_target_instance_list_empty.json
 
b/google-compute-engine/src/test/resources/aggregated_target_instance_list_empty.json
new file mode 100644
index 0000000..e1a852c
--- /dev/null
+++ 
b/google-compute-engine/src/test/resources/aggregated_target_instance_list_empty.json
@@ -0,0 +1,55 @@
+{
+ "kind": "compute#addressAggregatedList",
+ "selfLink": 
"https://www.googleapis.com/compute/v1/projects/studied-point-720/aggregated/addresses";,
+ "id": "projects/studied-point-720/aggregated/addresses",
+ "items": {
+  "regions/asia-east1": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'regions/asia-east1' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "regions/asia-east1"
+     }
+    ]
+   }
+  },
+  "regions/europe-west1": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'regions/europe-west1' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "regions/europe-west1"
+     }
+    ]
+   }
+  },
+  "regions/us-central1": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'regions/us-central1' on this 
page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "regions/us-central1"
+     }
+    ]
+   }
+  },
+  "global": {
+   "warning": {
+    "code": "NO_RESULTS_ON_PAGE",
+    "message": "There are no results for scope 'global' on this page.",
+    "data": [
+     {
+      "key": "scope",
+      "value": "global"
+     }
+    ]
+   }
+  }
+ }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/resources/target_instance_get.json
----------------------------------------------------------------------
diff --git a/google-compute-engine/src/test/resources/target_instance_get.json 
b/google-compute-engine/src/test/resources/target_instance_get.json
new file mode 100644
index 0000000..89607d8
--- /dev/null
+++ b/google-compute-engine/src/test/resources/target_instance_get.json
@@ -0,0 +1,11 @@
+{
+  "kind": "compute#targetInstance",
+  "id": 13050421646334304115,
+  "creationTimestamp": "2014-07-18T09:47:30.826-07:00",
+  "name": "target-instance-1",
+  "description": "A pretty cool target instance",
+  "zone": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a";,
+  "natPolicy": "NO_NAT",
+  "instance": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/instances/test-0";,
+  "selfLink": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/targetInstances/target-instance-1";
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/resources/target_instance_insert.json
----------------------------------------------------------------------
diff --git 
a/google-compute-engine/src/test/resources/target_instance_insert.json 
b/google-compute-engine/src/test/resources/target_instance_insert.json
new file mode 100644
index 0000000..9e76ef8
--- /dev/null
+++ b/google-compute-engine/src/test/resources/target_instance_insert.json
@@ -0,0 +1,6 @@
+{
+ "name": "test-target-instance",
+ "description": "This is a test",
+ "natPolicy": "NO_NAT",
+ "instance": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/instances/instance-1";
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/jclouds-labs-google/blob/e50999ec/google-compute-engine/src/test/resources/target_instance_list.json
----------------------------------------------------------------------
diff --git a/google-compute-engine/src/test/resources/target_instance_list.json 
b/google-compute-engine/src/test/resources/target_instance_list.json
new file mode 100644
index 0000000..7e5e2c2
--- /dev/null
+++ b/google-compute-engine/src/test/resources/target_instance_list.json
@@ -0,0 +1,30 @@
+{
+ "kind": "compute#targetInstanceList",
+ "selfLink": 
"https://www.googleapis.com/compute/v1/projects/studied-point-720/zones/us-central1-a/targetInstances";,
+ "id": "projects/studied-point-720/zones/us-central1-a/targetInstances",
+ "items": [
+  {
+
+   "kind": "compute#targetInstance",
+   "id": "13050421646334304115",
+   "creationTimestamp": "2014-07-18T09:47:30.826-07:00",
+   "name": "target-instance-1",
+   "description": "A pretty cool target instance",
+   "zone": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a";,
+   "natPolicy": "NO_NAT",
+   "instance": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/instances/test-0";,
+   "selfLink": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/targetInstances/target-instance-1";
+  },
+  {
+
+   "kind": "compute#targetInstance",
+   "id": "7362436693678237415",
+   "creationTimestamp": "2014-11-20T17:35:17.268-08:00",
+   "name": "target-instance-2",
+   "zone": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a";,
+   "natPolicy": "NO_NAT",
+   "instance": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/instances/test-3";,
+   "selfLink": 
"https://www.googleapis.com/compute/v1/projects/party/zones/us-central1-a/targetInstances/target-instance-2";
+  }
+ ]
+}
\ No newline at end of file

Reply via email to