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/08/11 22:46:03 UTC
[4/4] jclouds git commit: JCLOUDS-482: Add support for arbitrary CPU
and RAM
JCLOUDS-482: Add support for arbitrary CPU and RAM
This is a combination of 16 commits:
* First approach to ArbitraryCpuRamTemplateBuilderImpl
* Several fixes: refactoring some names, format, identation problems, some missing license headers and generateId method
* Refactored parse utility
* Added GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl to support GCE custom machine URI
* extracted hardware creation to automaticHardwareForCpuAndRam method
* Fixed ide automatic asterisk imports
* correcting WIP base case PR according to comments
* added machineTypeUriToHardware to set custom hardware in nodes
* fix checkstyle violations and other PR comments
* Set the providerId to custom machineType URI and fix adding node log
* Arbitrary hardware tests added to BaseTemplateBuilderLiveTest and GoogleComputeEngineTemplateBuilderLiveTest
* Added two more tests to BaseTemplateBuilderLiveTest
* Move repeated constants to TestUtils to reuse code
* Fix full path in the Hardware id and URI
* Add custom hardware tests to BaseComputeServiceLiveTest and GCEServiceLiveTest
* Change customHardware test to use buildTemplate and fix identation
Project: http://git-wip-us.apache.org/repos/asf/jclouds/repo
Commit: http://git-wip-us.apache.org/repos/asf/jclouds/commit/81e34856
Tree: http://git-wip-us.apache.org/repos/asf/jclouds/tree/81e34856
Diff: http://git-wip-us.apache.org/repos/asf/jclouds/diff/81e34856
Branch: refs/heads/gsoc2016-ivan
Commit: 81e348561d404e547fccce4b1217108b2c1419c4
Parents: 449c6d8
Author: Iv�n Lomba <iv...@gmail.com>
Authored: Sat Jun 18 20:27:12 2016 +0200
Committer: Ignasi Barrera <na...@apache.org>
Committed: Fri Aug 12 00:45:32 2016 +0200
----------------------------------------------------------------------
.../filesystem/FilesystemBlobStoreTest.java | 6 +-
.../FilesystemContainerIntegrationTest.java | 10 +-
.../FilesystemStorageStrategyImplTest.java | 6 +-
.../org/jclouds/filesystem/utils/TestUtils.java | 3 -
.../oauth/v2/AuthorizationApiLiveTest.java | 8 +-
.../org/jclouds/oauth/v2/OAuthTestUtils.java | 3 -
.../ArbitraryCpuRamTemplateBuilderImpl.java | 84 ++++++
.../domain/internal/TemplateBuilderImpl.java | 83 +++---
...desWithGroupEncodedIntoNameThenAddToSet.java | 4 +-
.../compute/util/AutomaticHardwareIdSpec.java | 72 +++++
.../ArbitraryCpuRamTemplateBuilderImplTest.java | 275 ++++++++++++++++++
.../internal/BaseComputeServiceLiveTest.java | 25 ++
.../internal/BaseTemplateBuilderLiveTest.java | 103 +++++++
.../util/AutomaticHardwareIdSpecTest.java | 52 ++++
.../test/java/org/jclouds/utils/TestUtils.java | 3 +
...GoogleComputeEngineServiceContextModule.java | 4 +
...ngineArbitraryCpuRamTemplateBuilderImpl.java | 59 ++++
.../functions/InstanceToNodeMetadata.java | 46 ++-
.../GoogleComputeEngineServiceLiveTest.java | 23 +-
...gleComputeEngineTemplateBuilderLiveTest.java | 15 +
...eArbitraryCpuRamTemplateBuilderImplTest.java | 278 +++++++++++++++++++
.../functions/InstanceToNodeMetadataTest.java | 39 ++-
22 files changed, 1123 insertions(+), 78 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/apis/filesystem/src/test/java/org/jclouds/filesystem/FilesystemBlobStoreTest.java
----------------------------------------------------------------------
diff --git a/apis/filesystem/src/test/java/org/jclouds/filesystem/FilesystemBlobStoreTest.java b/apis/filesystem/src/test/java/org/jclouds/filesystem/FilesystemBlobStoreTest.java
index 88704e3..d27924f 100644
--- a/apis/filesystem/src/test/java/org/jclouds/filesystem/FilesystemBlobStoreTest.java
+++ b/apis/filesystem/src/test/java/org/jclouds/filesystem/FilesystemBlobStoreTest.java
@@ -18,6 +18,8 @@ package org.jclouds.filesystem;
import static com.google.common.io.BaseEncoding.base16;
import static org.jclouds.filesystem.util.Utils.isMacOSX;
+import static org.jclouds.utils.TestUtils.NO_INVOCATIONS;
+import static org.jclouds.utils.TestUtils.SINGLE_NO_ARG_INVOCATION;
import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertFalse;
import static org.testng.Assert.assertNotNull;
@@ -912,7 +914,7 @@ public class FilesystemBlobStoreTest {
@DataProvider
public Object[][] ignoreOnMacOSX() {
- return isMacOSX() ? TestUtils.NO_INVOCATIONS
- : TestUtils.SINGLE_NO_ARG_INVOCATION;
+ return isMacOSX() ? NO_INVOCATIONS
+ : SINGLE_NO_ARG_INVOCATION;
}
}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/apis/filesystem/src/test/java/org/jclouds/filesystem/integration/FilesystemContainerIntegrationTest.java
----------------------------------------------------------------------
diff --git a/apis/filesystem/src/test/java/org/jclouds/filesystem/integration/FilesystemContainerIntegrationTest.java b/apis/filesystem/src/test/java/org/jclouds/filesystem/integration/FilesystemContainerIntegrationTest.java
index 7a701a0..7dfdd3a 100644
--- a/apis/filesystem/src/test/java/org/jclouds/filesystem/integration/FilesystemContainerIntegrationTest.java
+++ b/apis/filesystem/src/test/java/org/jclouds/filesystem/integration/FilesystemContainerIntegrationTest.java
@@ -19,6 +19,8 @@ package org.jclouds.filesystem.integration;
import static org.jclouds.blobstore.options.ListContainerOptions.Builder.maxResults;
import static org.jclouds.filesystem.util.Utils.isMacOSX;
import static org.testng.Assert.assertEquals;
+import static org.jclouds.utils.TestUtils.NO_INVOCATIONS;
+import static org.jclouds.utils.TestUtils.SINGLE_NO_ARG_INVOCATION;
import java.io.IOException;
import java.util.Properties;
@@ -165,14 +167,14 @@ public class FilesystemContainerIntegrationTest extends BaseContainerIntegration
@DataProvider
public Object[][] ignoreOnMacOSX() {
- return isMacOSX() ? TestUtils.NO_INVOCATIONS
- : TestUtils.SINGLE_NO_ARG_INVOCATION;
+ return isMacOSX() ? NO_INVOCATIONS
+ : SINGLE_NO_ARG_INVOCATION;
}
@DataProvider
public Object[][] ignoreOnWindows() {
- return TestUtils.isWindowsOs() ? TestUtils.NO_INVOCATIONS
- : TestUtils.SINGLE_NO_ARG_INVOCATION;
+ return TestUtils.isWindowsOs() ? NO_INVOCATIONS
+ : SINGLE_NO_ARG_INVOCATION;
}
@Override
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/apis/filesystem/src/test/java/org/jclouds/filesystem/strategy/internal/FilesystemStorageStrategyImplTest.java
----------------------------------------------------------------------
diff --git a/apis/filesystem/src/test/java/org/jclouds/filesystem/strategy/internal/FilesystemStorageStrategyImplTest.java b/apis/filesystem/src/test/java/org/jclouds/filesystem/strategy/internal/FilesystemStorageStrategyImplTest.java
index 3fdd855..9079fa0 100644
--- a/apis/filesystem/src/test/java/org/jclouds/filesystem/strategy/internal/FilesystemStorageStrategyImplTest.java
+++ b/apis/filesystem/src/test/java/org/jclouds/filesystem/strategy/internal/FilesystemStorageStrategyImplTest.java
@@ -17,6 +17,8 @@
package org.jclouds.filesystem.strategy.internal;
import static org.jclouds.filesystem.util.Utils.isMacOSX;
+import static org.jclouds.utils.TestUtils.NO_INVOCATIONS;
+import static org.jclouds.utils.TestUtils.SINGLE_NO_ARG_INVOCATION;
import static org.jclouds.utils.TestUtils.randomByteSource;
import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertFalse;
@@ -699,7 +701,7 @@ public class FilesystemStorageStrategyImplTest {
@DataProvider
public Object[][] ignoreOnMacOSX() {
- return isMacOSX() ? TestUtils.NO_INVOCATIONS
- : TestUtils.SINGLE_NO_ARG_INVOCATION;
+ return isMacOSX() ? NO_INVOCATIONS
+ : SINGLE_NO_ARG_INVOCATION;
}
}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/apis/filesystem/src/test/java/org/jclouds/filesystem/utils/TestUtils.java
----------------------------------------------------------------------
diff --git a/apis/filesystem/src/test/java/org/jclouds/filesystem/utils/TestUtils.java b/apis/filesystem/src/test/java/org/jclouds/filesystem/utils/TestUtils.java
index cd0276c..224c21e 100644
--- a/apis/filesystem/src/test/java/org/jclouds/filesystem/utils/TestUtils.java
+++ b/apis/filesystem/src/test/java/org/jclouds/filesystem/utils/TestUtils.java
@@ -54,9 +54,6 @@ public class TestUtils {
private static final Iterator<File> IMAGE_RESOURCES_ITERATOR =
Iterators.cycle(IMAGE_RESOURCES);
- public static final Object[][] NO_INVOCATIONS = new Object[0][0];
- public static final Object[][] SINGLE_NO_ARG_INVOCATION = { new Object[0] };
-
/**
* Generate a random blob key simple name (with no path in the key)
* @return
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/apis/oauth/src/test/java/org/jclouds/oauth/v2/AuthorizationApiLiveTest.java
----------------------------------------------------------------------
diff --git a/apis/oauth/src/test/java/org/jclouds/oauth/v2/AuthorizationApiLiveTest.java b/apis/oauth/src/test/java/org/jclouds/oauth/v2/AuthorizationApiLiveTest.java
index 5d0d7cf..0aba641 100644
--- a/apis/oauth/src/test/java/org/jclouds/oauth/v2/AuthorizationApiLiveTest.java
+++ b/apis/oauth/src/test/java/org/jclouds/oauth/v2/AuthorizationApiLiveTest.java
@@ -24,6 +24,8 @@ import static org.jclouds.oauth.v2.config.OAuthProperties.AUDIENCE;
import static org.jclouds.oauth.v2.config.OAuthProperties.CERTIFICATE;
import static org.jclouds.oauth.v2.config.OAuthProperties.CREDENTIAL_TYPE;
import static org.jclouds.providers.AnonymousProviderMetadata.forApiOnEndpoint;
+import static org.jclouds.utils.TestUtils.NO_INVOCATIONS;
+import static org.jclouds.utils.TestUtils.SINGLE_NO_ARG_INVOCATION;
import static org.testng.Assert.assertNotNull;
import java.util.Properties;
@@ -63,19 +65,19 @@ public class AuthorizationApiLiveTest extends BaseApiLiveTest<AuthorizationApi>
@DataProvider
public Object[][] onlyRunForP12PrivateKeyCredentials() {
return (CredentialType.fromValue(credentialType) == CredentialType.P12_PRIVATE_KEY_CREDENTIALS) ?
- OAuthTestUtils.SINGLE_NO_ARG_INVOCATION : OAuthTestUtils.NO_INVOCATIONS;
+ SINGLE_NO_ARG_INVOCATION : NO_INVOCATIONS;
}
@DataProvider
public Object[][] onlyRunForClientCredentialsSecret() {
return (CredentialType.fromValue(credentialType) == CredentialType.CLIENT_CREDENTIALS_SECRET) ?
- OAuthTestUtils.SINGLE_NO_ARG_INVOCATION : OAuthTestUtils.NO_INVOCATIONS;
+ SINGLE_NO_ARG_INVOCATION : NO_INVOCATIONS;
}
@DataProvider
public Object[][] onlyRunForClientCredentialsP12() {
return (CredentialType.fromValue(credentialType) == CredentialType.CLIENT_CREDENTIALS_P12_AND_CERTIFICATE) ?
- OAuthTestUtils.SINGLE_NO_ARG_INVOCATION : OAuthTestUtils.NO_INVOCATIONS;
+ SINGLE_NO_ARG_INVOCATION : NO_INVOCATIONS;
}
@Test(dataProvider = "onlyRunForP12PrivateKeyCredentials")
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/apis/oauth/src/test/java/org/jclouds/oauth/v2/OAuthTestUtils.java
----------------------------------------------------------------------
diff --git a/apis/oauth/src/test/java/org/jclouds/oauth/v2/OAuthTestUtils.java b/apis/oauth/src/test/java/org/jclouds/oauth/v2/OAuthTestUtils.java
index d15f8b0..920ff18 100644
--- a/apis/oauth/src/test/java/org/jclouds/oauth/v2/OAuthTestUtils.java
+++ b/apis/oauth/src/test/java/org/jclouds/oauth/v2/OAuthTestUtils.java
@@ -32,9 +32,6 @@ import com.google.common.io.Files;
public class OAuthTestUtils {
- public static final Object[][] NO_INVOCATIONS = new Object[0][0];
- public static final Object[][] SINGLE_NO_ARG_INVOCATION = { new Object[0] };
-
public static Properties defaultProperties(Properties properties) {
try {
properties = properties == null ? new Properties() : properties;
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/compute/src/main/java/org/jclouds/compute/domain/internal/ArbitraryCpuRamTemplateBuilderImpl.java
----------------------------------------------------------------------
diff --git a/compute/src/main/java/org/jclouds/compute/domain/internal/ArbitraryCpuRamTemplateBuilderImpl.java b/compute/src/main/java/org/jclouds/compute/domain/internal/ArbitraryCpuRamTemplateBuilderImpl.java
new file mode 100644
index 0000000..f99b991
--- /dev/null
+++ b/compute/src/main/java/org/jclouds/compute/domain/internal/ArbitraryCpuRamTemplateBuilderImpl.java
@@ -0,0 +1,84 @@
+/*
+ * 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.compute.domain.internal;
+
+import com.google.common.base.Supplier;
+import org.jclouds.collect.Memoized;
+import org.jclouds.compute.domain.Hardware;
+import org.jclouds.compute.domain.HardwareBuilder;
+import org.jclouds.compute.domain.Image;
+import org.jclouds.compute.domain.Processor;
+import org.jclouds.compute.domain.TemplateBuilder;
+import org.jclouds.compute.options.TemplateOptions;
+import org.jclouds.compute.util.AutomaticHardwareIdSpec;
+import org.jclouds.domain.Location;
+
+import javax.inject.Inject;
+import javax.inject.Named;
+import javax.inject.Provider;
+import java.util.NoSuchElementException;
+import java.util.Set;
+
+import static org.jclouds.compute.util.AutomaticHardwareIdSpec.automaticHardwareIdSpecBuilder;
+import static org.jclouds.compute.util.AutomaticHardwareIdSpec.isAutomaticId;
+import static org.jclouds.compute.util.AutomaticHardwareIdSpec.parseId;
+
+public class ArbitraryCpuRamTemplateBuilderImpl extends TemplateBuilderImpl {
+ @Inject
+ protected ArbitraryCpuRamTemplateBuilderImpl(@Memoized Supplier<Set<? extends Location>> locations,
+ @Memoized Supplier<Set<? extends Image>> images, @Memoized Supplier<Set<? extends Hardware>> hardwares,
+ Supplier<Location> defaultLocation, @Named("DEFAULT") Provider<TemplateOptions> optionsProvider,
+ @Named("DEFAULT") Provider<TemplateBuilder> defaultTemplateProvider) {
+ super(locations, images, hardwares, defaultLocation, optionsProvider, defaultTemplateProvider);
+ }
+
+ protected Hardware automaticHardwareForCpuAndRam(double cores, int ram) {
+ return new HardwareBuilder()
+ .id(automaticHardwareIdSpecBuilder(cores, ram).toString())
+ .ram(ram)
+ .processor(new Processor(cores, 1.0))
+ .build();
+ }
+
+ protected Hardware findHardwareWithId(Set<? extends Hardware> hardwaresToSearch) {
+ try {
+ return super.findHardwareWithId(hardwaresToSearch);
+ } catch (NoSuchElementException ex) {
+ if (isAutomaticId(hardwareId)) {
+ AutomaticHardwareIdSpec spec = parseId(hardwareId);
+ return automaticHardwareForCpuAndRam(spec.getCores(), spec.getRam());
+ }
+ else {
+ throw ex;
+ }
+ }
+ }
+
+ protected Hardware resolveHardware(Set<? extends Hardware> hardwarel, final Iterable<? extends Image> images) {
+ try {
+ return super.resolveHardware(hardwarel, images);
+ }
+ catch (NoSuchElementException ex) {
+ if (super.minCores != 0 && super.minRam != 0) {
+ return automaticHardwareForCpuAndRam(minCores, minRam);
+ }
+ else throw new IllegalArgumentException("No hardware profile matching the given criteria was found. If " +
+ "you want to use exact values, please set the minCores and minRam values", ex);
+ }
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/compute/src/main/java/org/jclouds/compute/domain/internal/TemplateBuilderImpl.java
----------------------------------------------------------------------
diff --git a/compute/src/main/java/org/jclouds/compute/domain/internal/TemplateBuilderImpl.java b/compute/src/main/java/org/jclouds/compute/domain/internal/TemplateBuilderImpl.java
index 2865409..f860674 100644
--- a/compute/src/main/java/org/jclouds/compute/domain/internal/TemplateBuilderImpl.java
+++ b/compute/src/main/java/org/jclouds/compute/domain/internal/TemplateBuilderImpl.java
@@ -16,33 +16,20 @@
*/
package org.jclouds.compute.domain.internal;
-import static com.google.common.base.Preconditions.checkArgument;
-import static com.google.common.base.Preconditions.checkNotNull;
-import static com.google.common.base.Preconditions.checkState;
-import static com.google.common.base.Predicates.and;
-import static com.google.common.collect.Iterables.filter;
-import static com.google.common.collect.Iterables.find;
-import static com.google.common.collect.Iterables.size;
-import static com.google.common.collect.Iterables.transform;
-import static com.google.common.collect.Iterables.tryFind;
-import static com.google.common.collect.Lists.newArrayList;
-import static java.lang.String.format;
-import static org.jclouds.compute.util.ComputeServiceUtils.getCores;
-import static org.jclouds.compute.util.ComputeServiceUtils.getCoresAndSpeed;
-import static org.jclouds.compute.util.ComputeServiceUtils.getSpace;
-
-import java.util.Comparator;
-import java.util.Iterator;
-import java.util.List;
-import java.util.NoSuchElementException;
-import java.util.Set;
-import java.util.regex.Pattern;
-
-import javax.annotation.Resource;
-import javax.inject.Inject;
-import javax.inject.Named;
-import javax.inject.Provider;
-
+import com.google.common.annotations.VisibleForTesting;
+import com.google.common.base.Function;
+import com.google.common.base.Objects;
+import com.google.common.base.Objects.ToStringHelper;
+import com.google.common.base.Optional;
+import com.google.common.base.Predicate;
+import com.google.common.base.Predicates;
+import com.google.common.base.Supplier;
+import com.google.common.collect.ComparisonChain;
+import com.google.common.collect.ImmutableList;
+import com.google.common.collect.ImmutableSet;
+import com.google.common.collect.Iterables;
+import com.google.common.collect.Ordering;
+import com.google.common.primitives.Doubles;
import org.jclouds.collect.Memoized;
import org.jclouds.compute.domain.ComputeMetadata;
import org.jclouds.compute.domain.Hardware;
@@ -59,20 +46,31 @@ import org.jclouds.compute.suppliers.ImageCacheSupplier;
import org.jclouds.domain.Location;
import org.jclouds.logging.Logger;
-import com.google.common.annotations.VisibleForTesting;
-import com.google.common.base.Function;
-import com.google.common.base.Objects;
-import com.google.common.base.Objects.ToStringHelper;
-import com.google.common.base.Optional;
-import com.google.common.base.Predicate;
-import com.google.common.base.Predicates;
-import com.google.common.base.Supplier;
-import com.google.common.collect.ComparisonChain;
-import com.google.common.collect.ImmutableList;
-import com.google.common.collect.ImmutableSet;
-import com.google.common.collect.Iterables;
-import com.google.common.collect.Ordering;
-import com.google.common.primitives.Doubles;
+import javax.annotation.Resource;
+import javax.inject.Inject;
+import javax.inject.Named;
+import javax.inject.Provider;
+import java.util.Comparator;
+import java.util.Iterator;
+import java.util.List;
+import java.util.NoSuchElementException;
+import java.util.Set;
+import java.util.regex.Pattern;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.base.Preconditions.checkState;
+import static com.google.common.base.Predicates.and;
+import static com.google.common.collect.Iterables.filter;
+import static com.google.common.collect.Iterables.find;
+import static com.google.common.collect.Iterables.size;
+import static com.google.common.collect.Iterables.transform;
+import static com.google.common.collect.Iterables.tryFind;
+import static com.google.common.collect.Lists.newArrayList;
+import static java.lang.String.format;
+import static org.jclouds.compute.util.ComputeServiceUtils.getCores;
+import static org.jclouds.compute.util.ComputeServiceUtils.getCoresAndSpeed;
+import static org.jclouds.compute.util.ComputeServiceUtils.getSpace;
public class TemplateBuilderImpl implements TemplateBuilder {
@Resource
@@ -348,7 +346,6 @@ public class TemplateBuilderImpl implements TemplateBuilder {
return "imageDescription(" + imageDescription + ")";
}
};
-
private final Predicate<Hardware> hardwareIdPredicate = new Predicate<Hardware>() {
@Override
public boolean apply(Hardware input) {
@@ -727,7 +724,7 @@ public class TemplateBuilderImpl implements TemplateBuilder {
return image.get();
}
- private Hardware findHardwareWithId(Set<? extends Hardware> hardwaresToSearch) {
+ protected Hardware findHardwareWithId(Set<? extends Hardware> hardwaresToSearch) {
Hardware hardware;
// TODO: switch to GetHardwareStrategy in version 1.5
hardware = tryFind(hardwaresToSearch, hardwareIdPredicate).orNull();
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/compute/src/main/java/org/jclouds/compute/strategy/impl/CreateNodesWithGroupEncodedIntoNameThenAddToSet.java
----------------------------------------------------------------------
diff --git a/compute/src/main/java/org/jclouds/compute/strategy/impl/CreateNodesWithGroupEncodedIntoNameThenAddToSet.java b/compute/src/main/java/org/jclouds/compute/strategy/impl/CreateNodesWithGroupEncodedIntoNameThenAddToSet.java
index e7f3384..6ac36c7 100644
--- a/compute/src/main/java/org/jclouds/compute/strategy/impl/CreateNodesWithGroupEncodedIntoNameThenAddToSet.java
+++ b/compute/src/main/java/org/jclouds/compute/strategy/impl/CreateNodesWithGroupEncodedIntoNameThenAddToSet.java
@@ -33,6 +33,7 @@ import javax.inject.Inject;
import javax.inject.Named;
import javax.inject.Singleton;
+import com.google.common.base.Objects;
import org.jclouds.Constants;
import org.jclouds.compute.config.CustomizationResponse;
import org.jclouds.compute.domain.ComputeMetadata;
@@ -75,7 +76,8 @@ public class CreateNodesWithGroupEncodedIntoNameThenAddToSet implements CreateNo
public AtomicReference<NodeMetadata> call() throws Exception {
NodeMetadata node = null;
logger.debug(">> adding node location(%s) name(%s) image(%s) hardware(%s)", template.getLocation().getId(),
- name, template.getImage().getProviderId(), template.getHardware().getProviderId());
+ name, Objects.firstNonNull(template.getImage().getProviderId(), template.getImage().getId()),
+ Objects.firstNonNull(template.getHardware().getProviderId(), template.getHardware().getId()));
node = addNodeWithGroupStrategy.createNodeWithGroupEncodedIntoName(group, name, template);
logger.debug("<< %s node(%s)", formatStatus(node), node.getId());
return new AtomicReference<NodeMetadata>(node);
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/compute/src/main/java/org/jclouds/compute/util/AutomaticHardwareIdSpec.java
----------------------------------------------------------------------
diff --git a/compute/src/main/java/org/jclouds/compute/util/AutomaticHardwareIdSpec.java b/compute/src/main/java/org/jclouds/compute/util/AutomaticHardwareIdSpec.java
new file mode 100644
index 0000000..6aaa44a
--- /dev/null
+++ b/compute/src/main/java/org/jclouds/compute/util/AutomaticHardwareIdSpec.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.compute.util;
+
+import com.google.common.base.Splitter;
+
+import java.util.Map;
+
+public class AutomaticHardwareIdSpec {
+
+ private double cores;
+ private int ram;
+
+ public static boolean isAutomaticId(String id) {
+ return id.startsWith("automatic:");
+ }
+
+ public static AutomaticHardwareIdSpec parseId(String hardwareId) {
+ AutomaticHardwareIdSpec spec = new AutomaticHardwareIdSpec();
+ String hardwareSpec = hardwareId.substring(10);
+ Map<String, String> specValues = Splitter.on(';')
+ .trimResults()
+ .omitEmptyStrings()
+ .withKeyValueSeparator('=')
+ .split(hardwareSpec);
+ if (!specValues.containsKey("ram") || !specValues.containsKey("cores")) {
+ throw new IllegalArgumentException(String.format("Omitted keys on hardwareId: %s. Please set number " +
+ "of cores and ram amount.", hardwareId));
+ }
+ spec.ram = Integer.parseInt(specValues.get("ram"));
+ spec.cores = Double.parseDouble(specValues.get("cores"));
+ return spec;
+ }
+
+ public static AutomaticHardwareIdSpec automaticHardwareIdSpecBuilder(double cores, int ram) {
+ AutomaticHardwareIdSpec spec = new AutomaticHardwareIdSpec();
+ if (cores == 0 || ram == 0) {
+ throw new IllegalArgumentException(String.format("Omitted or wrong minCores and minRam. If you" +
+ " want to use exact values, please set the minCores and minRam values."));
+ }
+ spec.cores = cores;
+ spec.ram = ram;
+ return spec;
+ }
+
+ @Override
+ public String toString() {
+ return String.format("automatic:cores=%s;ram=%s", cores, ram);
+ }
+
+ public double getCores() {
+ return cores;
+ }
+
+ public int getRam() {
+ return ram;
+ }
+}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/compute/src/test/java/org/jclouds/compute/domain/internal/ArbitraryCpuRamTemplateBuilderImplTest.java
----------------------------------------------------------------------
diff --git a/compute/src/test/java/org/jclouds/compute/domain/internal/ArbitraryCpuRamTemplateBuilderImplTest.java b/compute/src/test/java/org/jclouds/compute/domain/internal/ArbitraryCpuRamTemplateBuilderImplTest.java
new file mode 100644
index 0000000..568a60b
--- /dev/null
+++ b/compute/src/test/java/org/jclouds/compute/domain/internal/ArbitraryCpuRamTemplateBuilderImplTest.java
@@ -0,0 +1,275 @@
+/*
+ * 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.compute.domain.internal;
+
+import com.google.common.base.Supplier;
+import com.google.common.base.Suppliers;
+import com.google.common.collect.ImmutableSet;
+import com.google.common.util.concurrent.Atomics;
+import com.google.inject.Provider;
+import com.google.inject.util.Providers;
+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.Processor;
+import org.jclouds.compute.domain.Template;
+import org.jclouds.compute.domain.TemplateBuilder;
+import org.jclouds.compute.options.TemplateOptions;
+import org.jclouds.compute.strategy.GetImageStrategy;
+import org.jclouds.compute.suppliers.ImageCacheSupplier;
+import org.jclouds.domain.Location;
+import org.jclouds.domain.LocationBuilder;
+import org.jclouds.domain.LocationScope;
+import org.jclouds.rest.AuthorizationException;
+import org.testng.annotations.Test;
+
+import java.net.URI;
+import java.util.Set;
+
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.easymock.EasyMock.anyObject;
+import static org.easymock.EasyMock.createMock;
+import static org.easymock.EasyMock.expect;
+import static org.easymock.EasyMock.replay;
+
+@Test(groups = "unit", singleThreaded = true, testName = "ArbitraryCpuRamTemplateBuilderImplTest")
+public class ArbitraryCpuRamTemplateBuilderImplTest {
+ private Location provider = new LocationBuilder()
+ .scope(LocationScope.PROVIDER)
+ .id("generic-provider")
+ .description("generic-provider")
+ .build();
+
+ private Location region = new LocationBuilder()
+ .scope(LocationScope.REGION)
+ .id("us-east-1")
+ .description("us-east-1")
+ .parent(provider)
+ .build();
+
+ private OperatingSystem os = OperatingSystem.builder()
+ .name("osName")
+ .version("osVersion")
+ .description("osDescription")
+ .arch("X86_32")
+ .build();
+
+ private Image image = new ImageBuilder()
+ .id("imageId")
+ .providerId("imageId")
+ .name("imageName")
+ .description("imageDescription")
+ .version("imageVersion")
+ .operatingSystem(os)
+ .status(Image.Status.AVAILABLE)
+ .location(null)
+ .build();
+
+ private Hardware hardware = new HardwareBuilder()
+ .ram(2048)
+ .processor(new Processor(2, 1))
+ .id("hardwareId")
+ .name("hardwareName")
+ .location(region)
+ .uri(URI.create("uri"))
+ .build();
+
+ private final String errorMessage = "No hardware profile matching the given criteria was found. " +
+ "If you want to use exact values, please set the minCores and minRam values";
+
+ @Test
+ public void testAutoGeneratedHardwareFromId(){
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+
+ TemplateBuilderImpl templateBuilder = new ArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region),
+ optionsProvider, templateBuilderProvider);
+
+ Hardware hardware = templateBuilder.hardwareId("automatic:cores=2;ram=256").build().getHardware();
+ assertThat(hardware.getRam()).isEqualTo(256);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getId()).isEqualTo("automatic:cores=2.0;ram=256");
+ }
+
+ @Test
+ public void testAutoGeneratedHardwareWithMinCoresAndMinRam(){
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet.of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new ArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minRam(1024);
+ templateBuilder.minCores(4);
+ Template template = templateBuilder.build();
+ Hardware hardware = template.getHardware();
+ assertThat(hardware.getRam()).isEqualTo(1024);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(4.0);
+ assertThat(hardware.getId()).isEqualTo("automatic:cores=4.0;ram=1024");
+ }
+
+ @Test
+ public void testExistingHardwareProfileMatchHardwareProfileWithMinCoresMinRam() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new ArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minCores(2);
+ templateBuilder.minRam(1024);
+ Template template = templateBuilder.build();
+ Hardware hardware = template.getHardware();
+ assertThat(hardware.getRam()).isEqualTo(2048);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getId()).isEqualTo("hardwareId");
+ }
+
+ @Test(expectedExceptions = IllegalArgumentException.class, expectedExceptionsMessageRegExp = errorMessage)
+ public void testOnlyRamTest() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet.of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new ArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minRam(4096);
+ templateBuilder.build();
+ }
+
+ @Test(expectedExceptions = IllegalArgumentException.class, expectedExceptionsMessageRegExp = errorMessage)
+ public void testOnlyCoresTest() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new ArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minCores(4);
+ templateBuilder.build();
+ }
+
+ @Test
+ public void testOnlyRamMatchHardwareProfileTest() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet.of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new ArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minRam(1024);
+ templateBuilder.build();
+ assertThat(hardware.getRam()).isEqualTo(2048);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getId()).isEqualTo("hardwareId");
+ }
+
+ @Test
+ public void testOnlyCoresMatchHardwareProfileTest() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new ArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minCores(1);
+ templateBuilder.build();
+ assertThat(hardware.getRam()).isEqualTo(2048);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getId()).isEqualTo("hardwareId");
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/compute/src/test/java/org/jclouds/compute/internal/BaseComputeServiceLiveTest.java
----------------------------------------------------------------------
diff --git a/compute/src/test/java/org/jclouds/compute/internal/BaseComputeServiceLiveTest.java b/compute/src/test/java/org/jclouds/compute/internal/BaseComputeServiceLiveTest.java
index d720538..d598e79 100644
--- a/compute/src/test/java/org/jclouds/compute/internal/BaseComputeServiceLiveTest.java
+++ b/compute/src/test/java/org/jclouds/compute/internal/BaseComputeServiceLiveTest.java
@@ -33,6 +33,7 @@ import static java.lang.String.format;
import static java.lang.System.currentTimeMillis;
import static java.util.concurrent.TimeUnit.SECONDS;
import static java.util.logging.Logger.getAnonymousLogger;
+import static org.assertj.core.api.Assertions.assertThat;
import static org.jclouds.Constants.PROPERTY_USER_THREADS;
import static org.jclouds.compute.options.RunScriptOptions.Builder.nameTask;
import static org.jclouds.compute.options.RunScriptOptions.Builder.wrapInInitScript;
@@ -44,6 +45,8 @@ import static org.jclouds.compute.predicates.NodePredicates.inGroup;
import static org.jclouds.compute.predicates.NodePredicates.runningInGroup;
import static org.jclouds.compute.util.ComputeServiceUtils.getCores;
import static org.jclouds.util.Predicates2.retry;
+import static org.jclouds.utils.TestUtils.NO_INVOCATIONS;
+import static org.jclouds.utils.TestUtils.SINGLE_NO_ARG_INVOCATION;
import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertFalse;
import static org.testng.Assert.assertNotNull;
@@ -81,6 +84,7 @@ import org.jclouds.compute.domain.NodeMetadata.Status;
import org.jclouds.compute.domain.OperatingSystem;
import org.jclouds.compute.domain.Template;
import org.jclouds.compute.domain.TemplateBuilder;
+import org.jclouds.compute.domain.internal.ArbitraryCpuRamTemplateBuilderImpl;
import org.jclouds.compute.util.OpenSocketFinder;
import org.jclouds.domain.Credentials;
import org.jclouds.domain.Location;
@@ -96,6 +100,7 @@ import org.jclouds.ssh.SshClient;
import org.jclouds.ssh.SshException;
import org.testng.annotations.AfterClass;
import org.testng.annotations.BeforeGroups;
+import org.testng.annotations.DataProvider;
import org.testng.annotations.Test;
import com.google.common.base.Function;
@@ -937,6 +942,26 @@ public abstract class BaseComputeServiceLiveTest extends BaseComputeServiceConte
}
}
+ @DataProvider
+ public Object[][] onlyIfAutomaticHardwareSupported() {
+ return client.templateBuilder() instanceof ArbitraryCpuRamTemplateBuilderImpl ?
+ SINGLE_NO_ARG_INVOCATION : NO_INVOCATIONS;
+ }
+
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"})
+ public void testCreateNodeWithCustomHardware() throws Exception {
+ Template template = buildTemplate(templateBuilder()
+ .hardwareId("automatic:cores=2;ram=4096"));
+ try {
+ NodeMetadata node = getOnlyElement(client.createNodesInGroup("custom", 1, template));
+ assertThat(node.getHardware().getRam()).isEqualTo(4096);
+ assertThat(node.getHardware().getProcessors().get(0).getCores()).isEqualTo(2);
+ }
+ finally {
+ client.destroyNodesMatching(inGroup("custom"));
+ }
+ }
+
@AfterClass(groups = { "integration", "live" })
@Override
protected void tearDownContext() {
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/compute/src/test/java/org/jclouds/compute/internal/BaseTemplateBuilderLiveTest.java
----------------------------------------------------------------------
diff --git a/compute/src/test/java/org/jclouds/compute/internal/BaseTemplateBuilderLiveTest.java b/compute/src/test/java/org/jclouds/compute/internal/BaseTemplateBuilderLiveTest.java
index 29b543f..5e27d5a 100644
--- a/compute/src/test/java/org/jclouds/compute/internal/BaseTemplateBuilderLiveTest.java
+++ b/compute/src/test/java/org/jclouds/compute/internal/BaseTemplateBuilderLiveTest.java
@@ -16,7 +16,10 @@
*/
package org.jclouds.compute.internal;
+import static org.assertj.core.api.Assertions.assertThat;
import static org.jclouds.compute.util.ComputeServiceUtils.getCores;
+import static org.jclouds.utils.TestUtils.NO_INVOCATIONS;
+import static org.jclouds.utils.TestUtils.SINGLE_NO_ARG_INVOCATION;
import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertTrue;
@@ -29,10 +32,14 @@ import org.jclouds.compute.ComputeServiceContext;
import org.jclouds.compute.domain.Hardware;
import org.jclouds.compute.domain.OsFamily;
import org.jclouds.compute.domain.Template;
+import org.jclouds.compute.domain.internal.ArbitraryCpuRamTemplateBuilderImpl;
+import org.jclouds.compute.util.AutomaticHardwareIdSpec;
import org.jclouds.domain.Location;
import org.jclouds.domain.LocationScope;
import org.jclouds.domain.LoginCredentials;
import org.jclouds.rest.config.CredentialStoreModule;
+import org.testng.SkipException;
+import org.testng.annotations.DataProvider;
import org.testng.annotations.Test;
import com.google.common.base.Splitter;
@@ -225,4 +232,100 @@ public abstract class BaseTemplateBuilderLiveTest extends BaseComputeServiceCont
assertTrue(actual.getLocation().getScope().compareTo(expected.getLocation().getScope()) <= 0);
}
+ @DataProvider
+ public Object[][] onlyIfAutomaticHardwareSupported() {
+ return view.getComputeService().templateBuilder() instanceof ArbitraryCpuRamTemplateBuilderImpl ?
+ SINGLE_NO_ARG_INVOCATION : NO_INVOCATIONS;
+ }
+
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"})
+ public void testAutoGeneratedHardwareFromId() {
+ Template template = view.getComputeService().templateBuilder()
+ .hardwareId("automatic:cores=2;ram=1024").build();
+ assertThat(template.getHardware().getId()).isEqualTo("automatic:cores=2;ram=1024");
+ assertThat(template.getHardware().getRam()).isEqualTo(1024);
+ assertThat(template.getHardware().getProcessors().get(0).getCores()).isEqualTo(2);
+ }
+
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"})
+ public void testAutoGeneratedHardwareMatchHardwareProfile() {
+ if (!view.getComputeService().listHardwareProfiles().isEmpty()) {
+ Template template = view.getComputeService().templateBuilder()
+ .minRam(2048).minCores(2).build();
+ assertThat(AutomaticHardwareIdSpec.isAutomaticId(template.getHardware().getId())).isFalse();
+ assertThat(template.getHardware().getRam()).isGreaterThanOrEqualTo(2048);
+ assertThat(template.getHardware().getProcessors().get(0).getCores()).isGreaterThanOrEqualTo(2);
+ }
+ else {
+ throw new SkipException("Hardware profile list is empty, this provider can not match any hardware profile" +
+ "to the specified minRam and minCores.");
+ }
+ }
+
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"})
+ public void testAutoGeneratedHardwareWithMinCoresAndMinRam() {
+ if (view.getComputeService().listHardwareProfiles().isEmpty()) {
+ Template template = view.getComputeService().templateBuilder()
+ .minRam(2048).minCores(2).build();
+ assertThat(AutomaticHardwareIdSpec.isAutomaticId(template.getHardware().getId())).isTrue();
+ assertThat(template.getHardware().getRam()).isEqualTo(2048);
+ assertThat(template.getHardware().getProcessors().get(0).getCores()).isEqualTo(2);
+ }
+ else {
+ throw new SkipException("Hardware profile list not empty.");
+ }
+ }
+
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"})
+ public void testAutoGeneratedHardwareWithOnlyMinCoresMatchHardwareProfile() {
+ if (!view.getComputeService().listHardwareProfiles().isEmpty()) {
+ Template template = view.getComputeService().templateBuilder().minCores(4).build();
+ assertThat(AutomaticHardwareIdSpec.isAutomaticId(template.getHardware().getId())).isFalse();
+ assertThat(template.getHardware().getProcessors().get(0).getCores()).isGreaterThanOrEqualTo(4);
+ }
+ else {
+ throw new SkipException("Hardware profile list is empty, this provider can not match any hardware profile" +
+ "to the specified minRam and minCores.");
+ }
+ }
+
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"})
+ public void testAutoGeneratedHardwareWithOnlyMinRamMatchHardwareProfile() {
+ if (!view.getComputeService().listHardwareProfiles().isEmpty()) {
+ Template template = view.getComputeService().templateBuilder().minRam(4096).build();
+ assertThat(AutomaticHardwareIdSpec.isAutomaticId(template.getHardware().getId())).isFalse();
+ assertThat(template.getHardware().getRam()).isGreaterThanOrEqualTo(4096);
+ }
+ else {
+ throw new SkipException("Hardware profile list is empty, this provider can not match any hardware profile" +
+ "to the specified minRam and minCores.");
+ }
+ }
+
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"},
+ expectedExceptions = IllegalArgumentException.class,
+ expectedExceptionsMessageRegExp = "No hardware profile matching the given criteria was found. " +
+ "If you want to use exact values, please set the minCores and minRam values")
+ public void testAutoGeneratedHardwareWithOnlyMinRamNotMatchHardwareProfile() {
+ if (view.getComputeService().listHardwareProfiles().isEmpty()) {
+ view.getComputeService().templateBuilder().minRam(4096).build();
+ }
+ else {
+ throw new SkipException("Hardware profile list not empty.");
+ }
+ }
+
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"},
+ expectedExceptions = IllegalArgumentException.class,
+ expectedExceptionsMessageRegExp = "No hardware profile matching the given criteria was found. " +
+ "If you want to use exact values, please set the minCores and minRam values")
+ public void testAutoGeneratedHardwareWithOnlyMinCoresNotMatchHardwareProfile() {
+ if (view.getComputeService().listHardwareProfiles().isEmpty()) {
+ view.getComputeService().templateBuilder().minCores(4).build();
+ }
+ else {
+ throw new SkipException("Hardware profile list not empty.");
+ }
+ }
+
}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/compute/src/test/java/org/jclouds/compute/util/AutomaticHardwareIdSpecTest.java
----------------------------------------------------------------------
diff --git a/compute/src/test/java/org/jclouds/compute/util/AutomaticHardwareIdSpecTest.java b/compute/src/test/java/org/jclouds/compute/util/AutomaticHardwareIdSpecTest.java
new file mode 100644
index 0000000..9dc72a2
--- /dev/null
+++ b/compute/src/test/java/org/jclouds/compute/util/AutomaticHardwareIdSpecTest.java
@@ -0,0 +1,52 @@
+/*
+ * 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.compute.util;
+
+import org.testng.annotations.Test;
+
+import static org.assertj.core.api.Assertions.assertThat;
+
+@Test(groups = "unit", testName = "AutomaticHardwareIdSpecTest")
+public class AutomaticHardwareIdSpecTest {
+ @Test
+ public void isAutomaticIdTest() {
+ assertThat(AutomaticHardwareIdSpec.isAutomaticId("automatic:cores=2;ram=256")).isTrue();
+ }
+
+ @Test
+ public void isNotAutomaticId() {
+ assertThat(AutomaticHardwareIdSpec.isAutomaticId("Hi, I'm a non automatic id.")).isFalse();
+ }
+
+ @Test
+ public void parseAutomaticIdTest() {
+ AutomaticHardwareIdSpec parser = AutomaticHardwareIdSpec.parseId("automatic:cores=2;ram=256");
+ assertThat(parser.getRam()).isEqualTo(256);
+ assertThat(parser.getCores()).isEqualTo(2);
+ }
+
+ @Test(expectedExceptions = IllegalArgumentException.class)
+ public void parseAutomaticIdMissingValuesTest() {
+ AutomaticHardwareIdSpec.parseId("automatic:cores=2");
+ }
+
+ @Test
+ public void generateAutomaticIdTest() {
+ AutomaticHardwareIdSpec spec = AutomaticHardwareIdSpec.parseId("automatic:cores=2;ram=1024");
+ assertThat(spec.toString()).isEqualTo("automatic:cores=2.0;ram=1024");
+ }
+}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/core/src/test/java/org/jclouds/utils/TestUtils.java
----------------------------------------------------------------------
diff --git a/core/src/test/java/org/jclouds/utils/TestUtils.java b/core/src/test/java/org/jclouds/utils/TestUtils.java
index 7082346..cce923b 100644
--- a/core/src/test/java/org/jclouds/utils/TestUtils.java
+++ b/core/src/test/java/org/jclouds/utils/TestUtils.java
@@ -27,6 +27,9 @@ import com.google.common.io.ByteSource;
*/
public class TestUtils {
+ public static final Object[][] NO_INVOCATIONS = new Object[0][0];
+ public static final Object[][] SINGLE_NO_ARG_INVOCATION = { new Object[0] };
+
public static boolean isJava6() {
return System.getProperty("java.version", "").contains("1.6.");
}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/config/GoogleComputeEngineServiceContextModule.java
----------------------------------------------------------------------
diff --git a/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/config/GoogleComputeEngineServiceContextModule.java b/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/config/GoogleComputeEngineServiceContextModule.java
index 484df91..8c35f32 100644
--- a/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/config/GoogleComputeEngineServiceContextModule.java
+++ b/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/config/GoogleComputeEngineServiceContextModule.java
@@ -79,6 +79,8 @@ import com.google.inject.Injector;
import com.google.inject.Provides;
import com.google.inject.Scopes;
import com.google.inject.TypeLiteral;
+import org.jclouds.compute.domain.internal.TemplateBuilderImpl;
+import org.jclouds.googlecomputeengine.compute.domain.internal.GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl;
public final class GoogleComputeEngineServiceContextModule
extends ComputeServiceAdapterContextModule<Instance, MachineType, Image, Location> {
@@ -92,6 +94,8 @@ public final class GoogleComputeEngineServiceContextModule
bind(new TypeLiteral<ComputeServiceAdapter<Instance, MachineType, Image, Location>>() {
}).to(GoogleComputeEngineServiceAdapter.class);
+ bind(TemplateBuilderImpl.class).to(GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl.class);
+
// Use compute service to supply locations, which are always zones.
install(new LocationsFromComputeServiceAdapterModule<Instance, MachineType, Image, Location>() {
});
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/domain/internal/GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl.java
----------------------------------------------------------------------
diff --git a/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/domain/internal/GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl.java b/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/domain/internal/GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl.java
new file mode 100644
index 0000000..774dce9
--- /dev/null
+++ b/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/domain/internal/GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl.java
@@ -0,0 +1,59 @@
+/*
+ * 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.compute.domain.internal;
+
+import com.google.common.base.Supplier;
+import org.jclouds.collect.Memoized;
+import org.jclouds.compute.domain.Hardware;
+import org.jclouds.compute.domain.HardwareBuilder;
+import org.jclouds.compute.domain.Processor;
+import org.jclouds.compute.domain.TemplateBuilder;
+import org.jclouds.compute.domain.internal.ArbitraryCpuRamTemplateBuilderImpl;
+import org.jclouds.compute.options.TemplateOptions;
+import org.jclouds.domain.Location;
+
+import javax.inject.Inject;
+import javax.inject.Named;
+import javax.inject.Provider;
+import java.net.URI;
+import java.util.Set;
+
+public class GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl extends ArbitraryCpuRamTemplateBuilderImpl {
+ @Inject
+ protected GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl(@Memoized Supplier<Set<? extends Location>> locations,
+ @Memoized Supplier<Set<? extends org.jclouds.compute.domain.Image>> images,
+ @Memoized Supplier<Set<? extends Hardware>> hardwares, Supplier<Location> defaultLocation,
+ @Named("DEFAULT") Provider<TemplateOptions> optionsProvider,
+ @Named("DEFAULT") Provider<TemplateBuilder> defaultTemplateProvider) {
+ super(locations, images, hardwares, defaultLocation, optionsProvider, defaultTemplateProvider);
+ }
+
+ protected Hardware automaticHardwareForCpuAndRam(double cores, int ram) {
+ if (location == null) {
+ location = defaultLocation.get();
+ }
+ String uri = location.getDescription() + "/machineTypes/custom-" + (int)cores + "-" + ram;
+ return new HardwareBuilder()
+ .id(uri)
+ .ram(ram)
+ .processor(new Processor((int)cores, 1.0))
+ .providerId(uri)
+ .uri(URI.create(uri))
+ .build();
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/functions/InstanceToNodeMetadata.java
----------------------------------------------------------------------
diff --git a/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/functions/InstanceToNodeMetadata.java b/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/functions/InstanceToNodeMetadata.java
index 6f72bee..7e7407e 100644
--- a/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/functions/InstanceToNodeMetadata.java
+++ b/providers/google-compute-engine/src/main/java/org/jclouds/googlecomputeengine/compute/functions/InstanceToNodeMetadata.java
@@ -16,27 +16,30 @@
*/
package org.jclouds.googlecomputeengine.compute.functions;
-import static org.jclouds.compute.util.ComputeServiceUtils.groupFromMapOrName;
-
-import javax.inject.Inject;
-import java.net.URI;
-import java.util.List;
-import java.util.Map;
-
import com.google.common.base.Function;
+import com.google.common.base.Splitter;
import com.google.common.base.Supplier;
import com.google.common.cache.LoadingCache;
import com.google.common.collect.ImmutableList;
import org.jclouds.collect.Memoized;
import org.jclouds.compute.domain.Hardware;
+import org.jclouds.compute.domain.HardwareBuilder;
import org.jclouds.compute.domain.NodeMetadata;
import org.jclouds.compute.domain.NodeMetadata.Status;
import org.jclouds.compute.domain.NodeMetadataBuilder;
+import org.jclouds.compute.domain.Processor;
import org.jclouds.compute.functions.GroupNamingConvention;
import org.jclouds.domain.Location;
import org.jclouds.googlecomputeengine.domain.Image;
import org.jclouds.googlecomputeengine.domain.Instance;
+import javax.inject.Inject;
+import java.net.URI;
+import java.util.List;
+import java.util.Map;
+
+import static org.jclouds.compute.util.ComputeServiceUtils.groupFromMapOrName;
+
public final class InstanceToNodeMetadata implements Function<Instance, NodeMetadata> {
private final Map<Instance.Status, NodeMetadata.Status> toPortableNodeStatus;
@@ -73,13 +76,21 @@ public final class InstanceToNodeMetadata implements Function<Instance, NodeMeta
// a loading cache. That would be more expensive, but could ensure this isn't null.
Image image = diskURIToImage.getUnchecked(input.disks().get(0).source());
+ Hardware hardware;
+ if (isCustomMachineTypeURI(input.machineType())) {
+ hardware = machineTypeURIToCustomHardware(input.machineType());
+ }
+ else {
+ hardware = hardwares.get().get(input.machineType());
+ }
+
builder.id(input.selfLink().toString())
.name(input.name())
.providerId(input.id())
.hostname(input.name())
.location(zone)
.imageId(image != null ? image.selfLink().toString() : null)
- .hardware(hardwares.get().get(input.machineType()))
+ .hardware(hardware)
.status(input.status() != null ? toPortableNodeStatus.get(input.status()) : Status.UNRECOGNIZED)
.tags(input.tags().items())
.uri(input.selfLink())
@@ -111,4 +122,23 @@ public final class InstanceToNodeMetadata implements Function<Instance, NodeMeta
}
return publicAddressesBuilder.build();
}
+
+ public static boolean isCustomMachineTypeURI(URI machineType) {
+ return machineType.toString().contains("machineTypes/custom");
+ }
+
+ public static Hardware machineTypeURIToCustomHardware(URI machineType) {
+ String uri = machineType.toString();
+ String values = uri.substring(uri.lastIndexOf('/') + 8);
+ List<String> hardwareValues = Splitter.on('-')
+ .trimResults()
+ .splitToList(values);
+ return new HardwareBuilder()
+ .id(uri)
+ .providerId(uri)
+ .processor(new Processor(Double.parseDouble(hardwareValues.get(0)), 1.0))
+ .ram(Integer.parseInt(hardwareValues.get(1)))
+ .uri(machineType)
+ .build();
+ }
}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineServiceLiveTest.java
----------------------------------------------------------------------
diff --git a/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineServiceLiveTest.java b/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineServiceLiveTest.java
index ca381db..d8bd28e 100644
--- a/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineServiceLiveTest.java
+++ b/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineServiceLiveTest.java
@@ -17,6 +17,9 @@
package org.jclouds.googlecomputeengine.compute;
import static com.google.common.collect.Iterables.contains;
+import static com.google.common.collect.Iterables.getOnlyElement;
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.jclouds.compute.predicates.NodePredicates.inGroup;
import static org.jclouds.util.Strings2.toStringAndClose;
import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertFalse;
@@ -33,9 +36,9 @@ import com.google.inject.Module;
import org.jclouds.compute.ComputeServiceContext;
import org.jclouds.compute.domain.Hardware;
import org.jclouds.compute.domain.NodeMetadata;
+import org.jclouds.compute.domain.Template;
import org.jclouds.compute.internal.BaseComputeServiceLiveTest;
import org.jclouds.compute.options.TemplateOptions;
-import org.jclouds.compute.predicates.NodePredicates;
import org.jclouds.googlecloud.internal.TestProperties;
import org.jclouds.googlecomputeengine.GoogleComputeEngineApi;
import org.jclouds.googlecomputeengine.compute.options.GoogleComputeEngineTemplateOptions;
@@ -95,7 +98,7 @@ public class GoogleComputeEngineServiceLiveTest extends BaseComputeServiceLiveTe
assertTrue(instance.scheduling().preemptible());
} finally {
- client.destroyNodesMatching(NodePredicates.inGroup(group));
+ client.destroyNodesMatching(inGroup(group));
}
}
/**
@@ -152,4 +155,20 @@ public class GoogleComputeEngineServiceLiveTest extends BaseComputeServiceLiveTe
// Hardware profiles might not have volumes.
}
+ @Override
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"})
+ public void testCreateNodeWithCustomHardware() throws Exception {
+ Template template = buildTemplate(templateBuilder()
+ .hardwareId("automatic:cores=2;ram=4096"));
+ try {
+ NodeMetadata node = getOnlyElement(client.createNodesInGroup("custom", 1, template));
+ assertThat(node.getHardware().getRam()).isEqualTo(4096);
+ assertThat(node.getHardware().getProcessors().get(0).getCores()).isEqualTo(2);
+ assertThat(node.getHardware().getId()).isEqualTo(node.getLocation().getDescription() + "/machineTypes/custom-2-4096");
+ }
+ finally {
+ client.destroyNodesMatching(inGroup("custom"));
+ }
+ }
+
}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineTemplateBuilderLiveTest.java
----------------------------------------------------------------------
diff --git a/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineTemplateBuilderLiveTest.java b/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineTemplateBuilderLiveTest.java
index dbbedb3..a954e21 100644
--- a/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineTemplateBuilderLiveTest.java
+++ b/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/GoogleComputeEngineTemplateBuilderLiveTest.java
@@ -17,6 +17,7 @@
package org.jclouds.googlecomputeengine.compute;
import static com.google.common.base.Objects.firstNonNull;
+import static org.assertj.core.api.Assertions.assertThat;
import static org.jclouds.compute.domain.OsFamily.COREOS;
import static org.jclouds.compute.domain.OsFamily.DEBIAN;
import static org.jclouds.compute.domain.OsFamily.WINDOWS;
@@ -25,6 +26,7 @@ import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertTrue;
import java.io.IOException;
+import java.net.URI;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
@@ -76,4 +78,17 @@ public class GoogleComputeEngineTemplateBuilderLiveTest extends BaseTemplateBuil
return ImmutableSet.<String> of();
}
+ @Override
+ @Test(dataProvider = "onlyIfAutomaticHardwareSupported", groups = {"integration", "live"})
+ public void testAutoGeneratedHardwareFromId() {
+ Template template = view.getComputeService().templateBuilder()
+ .hardwareId("automatic:cores=2;ram=1024").build();
+ assertThat(template.getHardware().getId()).isEqualTo(template.getLocation()
+ .getDescription() + "/machineTypes/custom-2-1024");
+ assertThat(template.getHardware().getRam()).isEqualTo(1024);
+ assertThat(template.getHardware().getProcessors().get(0).getCores()).isEqualTo(2);
+ assertThat(template.getHardware().getUri()).isEqualTo(URI.create(template.getLocation()
+ .getDescription() + "/machineTypes/custom-2-1024"));
+ }
+
}
http://git-wip-us.apache.org/repos/asf/jclouds/blob/81e34856/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/domain/internal/GoogleComputeEngineArbitraryCpuRamTemplateBuilderImplTest.java
----------------------------------------------------------------------
diff --git a/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/domain/internal/GoogleComputeEngineArbitraryCpuRamTemplateBuilderImplTest.java b/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/domain/internal/GoogleComputeEngineArbitraryCpuRamTemplateBuilderImplTest.java
new file mode 100644
index 0000000..98b3144
--- /dev/null
+++ b/providers/google-compute-engine/src/test/java/org/jclouds/googlecomputeengine/compute/domain/internal/GoogleComputeEngineArbitraryCpuRamTemplateBuilderImplTest.java
@@ -0,0 +1,278 @@
+/*
+ * 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.compute.domain.internal;
+
+import com.google.common.base.Supplier;
+import com.google.common.base.Suppliers;
+import com.google.common.collect.ImmutableSet;
+import com.google.common.util.concurrent.Atomics;
+import com.google.inject.Provider;
+import com.google.inject.util.Providers;
+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.Processor;
+import org.jclouds.compute.domain.TemplateBuilder;
+import org.jclouds.compute.domain.internal.TemplateBuilderImpl;
+import org.jclouds.compute.options.TemplateOptions;
+import org.jclouds.compute.strategy.GetImageStrategy;
+import org.jclouds.compute.suppliers.ImageCacheSupplier;
+import org.jclouds.domain.Location;
+import org.jclouds.domain.LocationBuilder;
+import org.jclouds.domain.LocationScope;
+import org.jclouds.rest.AuthorizationException;
+import org.testng.annotations.Test;
+
+import java.net.URI;
+import java.util.Set;
+
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.easymock.EasyMock.anyObject;
+import static org.easymock.EasyMock.createMock;
+import static org.easymock.EasyMock.expect;
+import static org.easymock.EasyMock.replay;
+
+@Test(groups = "unit", singleThreaded = true, testName = "GoogleComputeEngineTemplateBuilderImplTest")
+public class GoogleComputeEngineArbitraryCpuRamTemplateBuilderImplTest {
+ private Location provider = new LocationBuilder()
+ .scope(LocationScope.PROVIDER)
+ .id("google-compute-engine")
+ .description("google-compute-engine")
+ .build();
+
+ private Location region = new LocationBuilder()
+ .scope(LocationScope.REGION)
+ .id("us-east-1")
+ .description("http://localhost/projects/party/zones/us-east-1")
+ .parent(provider)
+ .build();
+
+ private OperatingSystem os = OperatingSystem.builder()
+ .name("osName")
+ .version("osVersion")
+ .description("osDescription")
+ .arch("X86_32")
+ .build();
+
+ private Image image = new ImageBuilder()
+ .id("imageId")
+ .providerId("imageId")
+ .name("imageName")
+ .description("imageDescription")
+ .version("imageVersion")
+ .operatingSystem(os)
+ .status(Image.Status.AVAILABLE)
+ .location(null)
+ .build();
+
+ private Hardware hardware = new HardwareBuilder()
+ .ram(2048)
+ .processor(new Processor(2, 1))
+ .id("http://localhost/projects/party/zones/us-east-1/machineTypes/n2-standard-2")
+ .name("n2-standard-2")
+ .location(region)
+ .uri(URI.create("http://localhost/projects/party/zones/us-east-1/machineTypes/n2-standard-2"))
+ .build();
+
+ private final String errorMessage = "No hardware profile matching the given criteria was found. " +
+ "If you want to use exact values, please set the minCores and minRam values";
+
+ @Test
+ public void testAutoGeneratedHardwareFromIdTest(){
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet.of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+
+ TemplateBuilderImpl templateBuilder =
+ new GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl(locations, new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region),
+ optionsProvider, templateBuilderProvider);
+
+ Hardware hardware = templateBuilder.hardwareId("automatic:cores=2;ram=1024").build().getHardware();
+ assertThat(hardware.getRam()).isEqualTo(1024);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getUri()).isEqualTo(URI.create("http://localhost/projects/party/zones/us-east-1/machineTypes/custom-2-1024"));
+ assertThat(hardware.getId()).isEqualTo("http://localhost/projects/party/zones/us-east-1/machineTypes/custom-2-1024");
+ }
+
+ @Test
+ public void testAutoGeneratedHardwareWithMinCoresAndMinRamDontMatchTest() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minRam(4096);
+ templateBuilder.minCores(2);
+ Hardware hardware = templateBuilder.build().getHardware();
+ assertThat(hardware.getRam()).isEqualTo(4096);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getId()).isEqualTo("http://localhost/projects/party/zones/us-east-1/machineTypes/custom-2-4096");
+ }
+
+ @Test
+ public void testAutoGeneratedHardwareMatchHardwareProfile() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minRam(1024);
+ templateBuilder.minCores(2);
+ Hardware hardware = templateBuilder.build().getHardware();
+ assertThat(hardware.getRam()).isEqualTo(2048);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getId()).isEqualTo("http://localhost/projects/party/zones/us-east-1/machineTypes/n2-standard-2");
+ }
+
+ @Test(expectedExceptions = IllegalArgumentException.class, expectedExceptionsMessageRegExp = errorMessage)
+ public void testAutoGeneratedHardwareWithOnlyMinCoresTest() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minCores(4);
+ templateBuilder.build().getHardware();
+ }
+
+ @Test(expectedExceptions = IllegalArgumentException.class, expectedExceptionsMessageRegExp = errorMessage)
+ public void testAutoGeneratedHardwareWithOnlyMinRamTest() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minRam(4096);
+ templateBuilder.build().getHardware();
+ }
+
+ @Test
+ public void testAutoGeneratedHardwareWithOnlyMinCoresMatchedHardware() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minCores(2);
+ Hardware hardware = templateBuilder.build().getHardware();
+ assertThat(hardware.getRam()).isEqualTo(2048);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getId())
+ .isEqualTo("http://localhost/projects/party/zones/us-east-1/machineTypes/n2-standard-2");
+ }
+
+ @Test
+ public void testAutoGeneratedHardwareOnlyRamMatchHardwareProfile() {
+ Supplier<Set<? extends Location>> locations = Suppliers.<Set<? extends Location>> ofInstance(ImmutableSet
+ .of(region));
+ Supplier<Set<? extends Image>> images = Suppliers.<Set<? extends Image>> ofInstance(ImmutableSet.of(image));
+ Supplier<Set<? extends Hardware>> hardwares = Suppliers.<Set<? extends Hardware>> ofInstance(ImmutableSet
+ .<Hardware> of(hardware));
+ Provider<TemplateOptions> optionsProvider = createMock(Provider.class);
+ Provider<TemplateBuilder> templateBuilderProvider = createMock(Provider.class);
+ TemplateBuilder defaultTemplate = createMock(TemplateBuilder.class);
+ GetImageStrategy getImageStrategy = createMock(GetImageStrategy.class);
+
+ expect(optionsProvider.get()).andReturn(new TemplateOptions());
+ expect(getImageStrategy.getImage(anyObject(String.class))).andReturn(null);
+ replay(defaultTemplate, optionsProvider, templateBuilderProvider, getImageStrategy);
+ TemplateBuilderImpl templateBuilder = new GoogleComputeEngineArbitraryCpuRamTemplateBuilderImpl(locations,
+ new ImageCacheSupplier(images, 60,
+ Atomics.<AuthorizationException>newReference(), Providers.of(getImageStrategy)), hardwares,
+ Suppliers.ofInstance(region), optionsProvider, templateBuilderProvider);
+ templateBuilder.minRam(1024);
+ Hardware hardware = templateBuilder.build().getHardware();
+ assertThat(hardware.getRam()).isEqualTo(2048);
+ assertThat(hardware.getProcessors()).extracting("cores").containsExactly(2.0);
+ assertThat(hardware.getId())
+ .isEqualTo("http://localhost/projects/party/zones/us-east-1/machineTypes/n2-standard-2");
+ }
+
+}