Issue 383: started to resolve eCloud compatibility problems

This commit is contained in:
Adrian Cole 2010-10-31 18:41:26 -07:00
parent 5385374ddb
commit 1eda57537b
20 changed files with 268 additions and 133 deletions

View File

@ -408,6 +408,45 @@ public abstract class BaseComputeServiceLiveTest {
testGet(); testGet();
} }
@Test(enabled = true, dependsOnMethods = "testSuspendResume")
public void testListNodes() throws Exception {
for (ComputeMetadata node : client.listNodes()) {
assert node.getProviderId() != null;
assert node.getLocation() != null;
assertEquals(node.getType(), ComputeType.NODE);
}
}
@Test(enabled = true, dependsOnMethods = "testSuspendResume")
public void testGetNodesWithDetails() throws Exception {
for (NodeMetadata node : client.listNodesDetailsMatching(all())) {
assert node.getProviderId() != null : node;
assert node.getLocation() != null : node;
assertEquals(node.getType(), ComputeType.NODE);
assert node instanceof NodeMetadata;
NodeMetadata nodeMetadata = (NodeMetadata) node;
assert nodeMetadata.getProviderId() != null : nodeMetadata;
// nullable
// assert nodeMetadata.getImage() != null : node;
// user specified name is not always supported
// assert nodeMetadata.getName() != null : nodeMetadata;
if (nodeMetadata.getState() == NodeState.RUNNING) {
assert nodeMetadata.getPublicAddresses() != null : nodeMetadata;
assert nodeMetadata.getPublicAddresses().size() > 0 || nodeMetadata.getPrivateAddresses().size() > 0 : nodeMetadata;
assertNotNull(nodeMetadata.getPrivateAddresses());
}
}
}
@Test(enabled = true, dependsOnMethods = { "testListNodes", "testGetNodesWithDetails" })
public void testDestroyNodes() {
client.destroyNodesMatching(withTag(tag));
for (NodeMetadata node : filter(client.listNodesDetailsMatching(all()), withTag(tag))) {
assert node.getState() == NodeState.TERMINATED : node;
assertEquals(context.getCredentialStore().get("node#" + node.getId()), null);
}
}
private Set<? extends NodeMetadata> refreshNodes() { private Set<? extends NodeMetadata> refreshNodes() {
return filter(client.listNodesDetailsMatching(all()), and(withTag(tag), not(TERMINATED))); return filter(client.listNodesDetailsMatching(all()), and(withTag(tag), not(TERMINATED)));
} }
@ -445,34 +484,6 @@ public abstract class BaseComputeServiceLiveTest {
assert t.getOptions().isIncludeMetadata() : "The metadata option should be 'true' " + "for the created template"; assert t.getOptions().isIncludeMetadata() : "The metadata option should be 'true' " + "for the created template";
} }
public void testListNodes() throws Exception {
for (ComputeMetadata node : client.listNodes()) {
assert node.getProviderId() != null;
assert node.getLocation() != null;
assertEquals(node.getType(), ComputeType.NODE);
}
}
public void testGetNodesWithDetails() throws Exception {
for (NodeMetadata node : client.listNodesDetailsMatching(all())) {
assert node.getProviderId() != null : node;
assert node.getLocation() != null : node;
assertEquals(node.getType(), ComputeType.NODE);
assert node instanceof NodeMetadata;
NodeMetadata nodeMetadata = (NodeMetadata) node;
assert nodeMetadata.getProviderId() != null : nodeMetadata;
// nullable
// assert nodeMetadata.getImage() != null : node;
// user specified name is not always supported
// assert nodeMetadata.getName() != null : nodeMetadata;
if (nodeMetadata.getState() == NodeState.RUNNING) {
assert nodeMetadata.getPublicAddresses() != null : nodeMetadata;
assert nodeMetadata.getPublicAddresses().size() > 0 || nodeMetadata.getPrivateAddresses().size() > 0 : nodeMetadata;
assertNotNull(nodeMetadata.getPrivateAddresses());
}
}
}
public void testListImages() throws Exception { public void testListImages() throws Exception {
for (Image image : client.listImages()) { for (Image image : client.listImages()) {
assert image.getProviderId() != null : image; assert image.getProviderId() != null : image;
@ -606,11 +617,7 @@ public abstract class BaseComputeServiceLiveTest {
@AfterTest @AfterTest
protected void cleanup() throws InterruptedException, ExecutionException, TimeoutException { protected void cleanup() throws InterruptedException, ExecutionException, TimeoutException {
if (nodes != null) { if (nodes != null) {
client.destroyNodesMatching(withTag(tag)); testDestroyNodes();
for (NodeMetadata node : filter(client.listNodesDetailsMatching(all()), withTag(tag))) {
assert node.getState() == NodeState.TERMINATED : node;
assertEquals(context.getCredentialStore().get("node#" + node.getId()), null);
}
} }
context.close(); context.close();
} }

View File

@ -371,6 +371,21 @@ public class StubComputeServiceIntegrationTest extends BaseComputeServiceLiveTes
super.testTemplateMatch(); super.testTemplateMatch();
} }
@Override
public void testGetNodesWithDetails() throws Exception {
super.testGetNodesWithDetails();
}
@Override
public void testListNodes() throws Exception {
super.testListNodes();
}
@Override
public void testDestroyNodes() {
super.testDestroyNodes();
}
@Override @Override
protected void cleanup() throws InterruptedException, ExecutionException, TimeoutException { protected void cleanup() throws InterruptedException, ExecutionException, TimeoutException {
super.cleanup(); super.cleanup();

View File

@ -22,6 +22,9 @@ package org.jclouds.vcloud.compute.functions;
import static com.google.common.base.Preconditions.checkNotNull; import static com.google.common.base.Preconditions.checkNotNull;
import static org.jclouds.compute.util.ComputeServiceUtils.parseOsFamilyOrNull; import static org.jclouds.compute.util.ComputeServiceUtils.parseOsFamilyOrNull;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.inject.Inject; import javax.inject.Inject;
import org.jclouds.compute.domain.Image; import org.jclouds.compute.domain.Image;
@ -44,7 +47,7 @@ public class ImageForVCloudExpressVAppTemplate implements Function<VCloudExpress
@Inject @Inject
protected ImageForVCloudExpressVAppTemplate(FindLocationForResource findLocationForResource, protected ImageForVCloudExpressVAppTemplate(FindLocationForResource findLocationForResource,
PopulateDefaultLoginCredentialsForImageStrategy credentialsProvider) { PopulateDefaultLoginCredentialsForImageStrategy credentialsProvider) {
this.findLocationForResource = checkNotNull(findLocationForResource, "findLocationForResource"); this.findLocationForResource = checkNotNull(findLocationForResource, "findLocationForResource");
this.credentialsProvider = checkNotNull(credentialsProvider, "credentialsProvider"); this.credentialsProvider = checkNotNull(credentialsProvider, "credentialsProvider");
} }
@ -67,11 +70,17 @@ public class ImageForVCloudExpressVAppTemplate implements Function<VCloudExpress
return builder.build(); return builder.build();
} }
public static final Pattern OS_PATTERN = Pattern.compile("(([^ ]*) ([0-9.]+) ?.*)");
protected OperatingSystem parseOs(VCloudExpressVAppTemplate from) { protected OperatingSystem parseOs(VCloudExpressVAppTemplate from) {
OperatingSystemBuilder builder = new OperatingSystemBuilder(); OperatingSystemBuilder builder = new OperatingSystemBuilder();
builder.family(parseOsFamilyOrNull("vcloudexpress", checkNotNull(from, "vapp template").getName())); builder.family(parseOsFamilyOrNull("vcloudexpress", checkNotNull(from, "vapp template").getName()));
builder.description(from.getName()); builder.description(from.getName());
builder.is64Bit(from.getName().indexOf("64") != -1); builder.is64Bit(from.getName().indexOf("64") != -1);
Matcher matcher = OS_PATTERN.matcher(from.getName());
if (matcher.find()) {
builder.version(matcher.group(3));
}
return builder.build(); return builder.build();
} }

View File

@ -174,7 +174,8 @@ public class CommonVCloudRestClientModule<S extends CommonVCloudClient, A extend
@Provides @Provides
@org.jclouds.vcloud.endpoints.VDC @org.jclouds.vcloud.endpoints.VDC
@Singleton @Singleton
protected String provideDefaultVDCName(@org.jclouds.vcloud.endpoints.VDC Supplier<Map<String, String>> vDCtoOrgSupplier) { protected String provideDefaultVDCName(
@org.jclouds.vcloud.endpoints.VDC Supplier<Map<String, String>> vDCtoOrgSupplier) {
Map<String, String> vDCtoOrg = vDCtoOrgSupplier.get(); Map<String, String> vDCtoOrg = vDCtoOrgSupplier.get();
checkState(vDCtoOrg.keySet().size() > 0, "No vdcs present!"); checkState(vDCtoOrg.keySet().size() > 0, "No vdcs present!");
return get(vDCtoOrg.keySet(), 0); return get(vDCtoOrg.keySet(), 0);
@ -408,12 +409,11 @@ public class CommonVCloudRestClientModule<S extends CommonVCloudClient, A extend
@Provides @Provides
@Network @Network
@Singleton @Singleton
protected URI provideDefaultNetwork(@org.jclouds.vcloud.endpoints.VDC URI defaultVDC, CommonVCloudClient client, protected URI provideDefaultNetwork(@org.jclouds.vcloud.endpoints.VDC URI defaultVDC, Injector injector) {
Injector injector) {
if (authException.get() != null) if (authException.get() != null)
throw authException.get(); throw authException.get();
try { try {
org.jclouds.vcloud.domain.VDC vDC = client.getVDC(defaultVDC); org.jclouds.vcloud.domain.VDC vDC = injector.getInstance(CommonVCloudClient.class).getVDC(defaultVDC);
Map<String, ReferenceType> networks = vDC.getAvailableNetworks(); Map<String, ReferenceType> networks = vDC.getAvailableNetworks();
checkState(networks.size() > 0, "No networks present in vDC: " + vDC.getName()); checkState(networks.size() > 0, "No networks present in vDC: " + vDC.getName());
if (networks.size() == 1) if (networks.size() == 1)
@ -425,18 +425,7 @@ public class CommonVCloudRestClientModule<S extends CommonVCloudClient, A extend
checkState(network != null, String.format("network named %s not in %s", networkName, networks.keySet())); checkState(network != null, String.format("network named %s not in %s", networkName, networks.keySet()));
return network.getHref(); return network.getHref();
} catch (ConfigurationException e) { } catch (ConfigurationException e) {
// TODO FIXME XXX: In Terremark Enterprise environment with multiple VDC's this does not return findDefaultNetworkForVDC(vDC, networks, injector);
// work well.
// Each VDC will have differnt network subnets. So we cannot assume the default VDC's
// networks will
// work with non-default VDC's. So make PROPERTY_VCLOUD_DEFAULT_NETWORK optional. If
// this property
// is not set, they are expected to add NetworkConfig to the options when launching a
// server.
return null;
// throw new
// IllegalStateException(String.format("you must specify the property %s as one of %s",
// PROPERTY_VCLOUD_DEFAULT_NETWORK, networks.keySet()), e);
} }
} catch (AuthorizationException e) { } catch (AuthorizationException e) {
authException.set(e); authException.set(e);
@ -444,6 +433,12 @@ public class CommonVCloudRestClientModule<S extends CommonVCloudClient, A extend
} }
} }
protected URI findDefaultNetworkForVDC(org.jclouds.vcloud.domain.VDC vDC, Map<String, ReferenceType> networks,
Injector injector) {
logger.warn("default network for vdc %s not set", vDC.getName());
return Iterables.getLast(networks.values()).getHref();
}
@Provides @Provides
@Singleton @Singleton
protected Org provideOrg(CommonVCloudClient discovery) { protected Org provideOrg(CommonVCloudClient discovery) {

View File

@ -216,7 +216,6 @@ public class VCloudAsyncClientTest extends RestClientTest<VCloudAsyncClient> {
checkFilters(request); checkFilters(request);
} }
public void testCaptureVAppInVDC() throws SecurityException, NoSuchMethodException, IOException { public void testCaptureVAppInVDC() throws SecurityException, NoSuchMethodException, IOException {
Method method = VCloudAsyncClient.class.getMethod("captureVAppInVDC", URI.class, URI.class, String.class, Method method = VCloudAsyncClient.class.getMethod("captureVAppInVDC", URI.class, URI.class, String.class,
CaptureVAppOptions[].class); CaptureVAppOptions[].class);
@ -242,8 +241,8 @@ public class VCloudAsyncClientTest extends RestClientTest<VCloudAsyncClient> {
CaptureVAppOptions[].class); CaptureVAppOptions[].class);
HttpRequest request = processor.createRequest(method, URI HttpRequest request = processor.createRequest(method, URI
.create("https://vcenterprise.bluelock.com/api/v1.0/vdc/1"), URI .create("https://vcenterprise.bluelock.com/api/v1.0/vdc/1"), URI
.create("https://vcenterprise.bluelock.com/api/v1.0/vapp/201"), "my-template", .create("https://vcenterprise.bluelock.com/api/v1.0/vapp/201"), "my-template", new CaptureVAppOptions()
new CaptureVAppOptions().withDescription("The description of the new vApp Template")); .withDescription("The description of the new vApp Template"));
assertRequestLineEquals(request, assertRequestLineEquals(request,
"POST https://vcenterprise.bluelock.com/api/v1.0/vdc/1/action/captureVApp HTTP/1.1"); "POST https://vcenterprise.bluelock.com/api/v1.0/vdc/1/action/captureVApp HTTP/1.1");
@ -258,8 +257,6 @@ public class VCloudAsyncClientTest extends RestClientTest<VCloudAsyncClient> {
checkFilters(request); checkFilters(request);
} }
public void testlistOrgs() throws SecurityException, NoSuchMethodException, IOException { public void testlistOrgs() throws SecurityException, NoSuchMethodException, IOException {
Method method = VCloudAsyncClient.class.getMethod("listOrgs"); Method method = VCloudAsyncClient.class.getMethod("listOrgs");
HttpRequest request = processor.createRequest(method); HttpRequest request = processor.createRequest(method);
@ -857,12 +854,13 @@ public class VCloudAsyncClientTest extends RestClientTest<VCloudAsyncClient> {
} }
@Override @Override
protected String provideDefaultVDCName(@org.jclouds.vcloud.endpoints.VDC Supplier<Map<String, String>> vDCtoOrgSupplier) { protected String provideDefaultVDCName(
@org.jclouds.vcloud.endpoints.VDC Supplier<Map<String, String>> vDCtoOrgSupplier) {
return "vdc"; return "vdc";
} }
@Override @Override
protected URI provideDefaultNetwork(URI vdc, CommonVCloudClient client, Injector injector) { protected URI provideDefaultNetwork(URI vdc, Injector injector) {
return URI.create("https://vcenterprise.bluelock.com/api/v1.0/network/1990"); return URI.create("https://vcenterprise.bluelock.com/api/v1.0/network/1990");
} }

View File

@ -694,7 +694,7 @@ public class VCloudExpressAsyncClientTest extends RestClientTest<VCloudExpressAs
} }
@Override @Override
protected URI provideDefaultNetwork(URI vdc, CommonVCloudClient client, Injector injector) { protected URI provideDefaultNetwork(URI vdc, Injector injector) {
return URI.create("https://vcloud.safesecureweb.com/network/1990"); return URI.create("https://vcloud.safesecureweb.com/network/1990");
} }

View File

@ -25,7 +25,7 @@ import java.util.Properties;
import org.jclouds.http.config.JavaUrlHttpCommandExecutorServiceModule; import org.jclouds.http.config.JavaUrlHttpCommandExecutorServiceModule;
import org.jclouds.logging.jdk.config.JDKLoggingModule; import org.jclouds.logging.jdk.config.JDKLoggingModule;
import org.jclouds.vcloud.VCloudExpressContextBuilder; import org.jclouds.vcloud.VCloudExpressContextBuilder;
import org.jclouds.vcloud.compute.config.VCloudExpressComputeServiceContextModule; import org.jclouds.vcloud.terremark.compute.config.TerremarkVCloudComputeServiceContextModule;
import org.jclouds.vcloud.terremark.config.TerremarkECloudRestClientModule; import org.jclouds.vcloud.terremark.config.TerremarkECloudRestClientModule;
import com.google.inject.Injector; import com.google.inject.Injector;
@ -52,8 +52,7 @@ public class TerremarkECloudContextBuilder extends VCloudExpressContextBuilder {
@Override @Override
protected void addContextModule(List<Module> modules) { protected void addContextModule(List<Module> modules) {
// TODO make ecloud version which retrieves passwords from the vapptemplate description modules.add(new TerremarkVCloudComputeServiceContextModule());
modules.add(new VCloudExpressComputeServiceContextModule());
} }
@Override @Override

View File

@ -37,6 +37,7 @@ import javax.inject.Singleton;
import org.jclouds.compute.domain.NodeState; import org.jclouds.compute.domain.NodeState;
import org.jclouds.compute.strategy.PopulateDefaultLoginCredentialsForImageStrategy; import org.jclouds.compute.strategy.PopulateDefaultLoginCredentialsForImageStrategy;
import org.jclouds.domain.Credentials; import org.jclouds.domain.Credentials;
import org.jclouds.http.HttpResponseException;
import org.jclouds.vcloud.compute.internal.VCloudExpressComputeClientImpl; import org.jclouds.vcloud.compute.internal.VCloudExpressComputeClientImpl;
import org.jclouds.vcloud.domain.Status; import org.jclouds.vcloud.domain.Status;
import org.jclouds.vcloud.domain.Task; import org.jclouds.vcloud.domain.Task;
@ -46,6 +47,7 @@ import org.jclouds.vcloud.domain.VCloudExpressVApp;
import org.jclouds.vcloud.domain.VCloudExpressVAppTemplate; import org.jclouds.vcloud.domain.VCloudExpressVAppTemplate;
import org.jclouds.vcloud.options.InstantiateVAppTemplateOptions; import org.jclouds.vcloud.options.InstantiateVAppTemplateOptions;
import org.jclouds.vcloud.terremark.TerremarkECloudClient; import org.jclouds.vcloud.terremark.TerremarkECloudClient;
import org.jclouds.vcloud.terremark.TerremarkVCloudClient;
import org.jclouds.vcloud.terremark.TerremarkVCloudExpressClient; import org.jclouds.vcloud.terremark.TerremarkVCloudExpressClient;
import org.jclouds.vcloud.terremark.domain.InternetService; import org.jclouds.vcloud.terremark.domain.InternetService;
import org.jclouds.vcloud.terremark.domain.Node; import org.jclouds.vcloud.terremark.domain.Node;
@ -63,16 +65,16 @@ import com.google.common.collect.Sets;
@Singleton @Singleton
public class TerremarkVCloudComputeClient extends VCloudExpressComputeClientImpl { public class TerremarkVCloudComputeClient extends VCloudExpressComputeClientImpl {
protected final TerremarkVCloudExpressClient client; protected final TerremarkVCloudClient client;
protected final PopulateDefaultLoginCredentialsForImageStrategy credentialsProvider; protected final PopulateDefaultLoginCredentialsForImageStrategy credentialsProvider;
protected final Provider<String> passwordGenerator; protected final Provider<String> passwordGenerator;
protected final Map<String, Credentials> credentialStore; protected final Map<String, Credentials> credentialStore;
@Inject @Inject
protected TerremarkVCloudComputeClient(TerremarkVCloudExpressClient client, protected TerremarkVCloudComputeClient(TerremarkVCloudClient client,
PopulateDefaultLoginCredentialsForImageStrategy credentialsProvider, PopulateDefaultLoginCredentialsForImageStrategy credentialsProvider,
@Named("PASSWORD") Provider<String> passwordGenerator, Predicate<URI> successTester, @Named("PASSWORD") Provider<String> passwordGenerator, Predicate<URI> successTester,
Map<Status, NodeState> vAppStatusToNodeState, Map<String, Credentials> credentialStore) { Map<Status, NodeState> vAppStatusToNodeState, Map<String, Credentials> credentialStore) {
super(client, successTester, vAppStatusToNodeState); super(client, successTester, vAppStatusToNodeState);
this.client = client; this.client = client;
this.credentialsProvider = credentialsProvider; this.credentialsProvider = credentialsProvider;
@ -82,7 +84,7 @@ public class TerremarkVCloudComputeClient extends VCloudExpressComputeClientImpl
@Override @Override
public VCloudExpressVApp start(@Nullable URI VDC, URI templateId, String name, public VCloudExpressVApp start(@Nullable URI VDC, URI templateId, String name,
InstantiateVAppTemplateOptions options, int... portsToOpen) { InstantiateVAppTemplateOptions options, int... portsToOpen) {
if (options.getDiskSizeKilobytes() != null) { if (options.getDiskSizeKilobytes() != null) {
logger.warn("trmk does not support resizing the primary disk; unsetting disk size"); logger.warn("trmk does not support resizing the primary disk; unsetting disk size");
} }
@ -92,7 +94,7 @@ public class TerremarkVCloudComputeClient extends VCloudExpressComputeClientImpl
String password = null; String password = null;
VCloudExpressVAppTemplate template = client.getVAppTemplate(templateId); VCloudExpressVAppTemplate template = client.getVAppTemplate(templateId);
if (template.getDescription().indexOf("Windows") != -1 if (template.getDescription().indexOf("Windows") != -1
&& options instanceof TerremarkInstantiateVAppTemplateOptions) { && options instanceof TerremarkInstantiateVAppTemplateOptions) {
password = passwordGenerator.get(); password = passwordGenerator.get();
TerremarkInstantiateVAppTemplateOptions.class.cast(options).getProperties().put("password", password); TerremarkInstantiateVAppTemplateOptions.class.cast(options).getProperties().put("password", password);
} }
@ -100,8 +102,8 @@ public class TerremarkVCloudComputeClient extends VCloudExpressComputeClientImpl
VCloudExpressVApp vAppResponse = super.start(VDC, templateId, name, options, portsToOpen); VCloudExpressVApp vAppResponse = super.start(VDC, templateId, name, options, portsToOpen);
if (password != null) { if (password != null) {
credentialStore.put("node#" + vAppResponse.getHref().toASCIIString(), new Credentials(defaultCredentials.identity, credentialStore.put("node#" + vAppResponse.getHref().toASCIIString(), new Credentials(
password)); defaultCredentials.identity, password));
} }
if (portsToOpen.length > 0) if (portsToOpen.length > 0)
createPublicAddressMappedToPorts(vAppResponse.getHref(), portsToOpen); createPublicAddressMappedToPorts(vAppResponse.getHref(), portsToOpen);
@ -116,51 +118,67 @@ public class TerremarkVCloudComputeClient extends VCloudExpressComputeClientImpl
InternetService is = null; InternetService is = null;
Protocol protocol; Protocol protocol;
switch (port) { switch (port) {
case 22: case 22:
protocol = Protocol.TCP; protocol = Protocol.TCP;
break; break;
case 80: case 80:
case 8080: case 8080:
protocol = Protocol.HTTP; protocol = Protocol.HTTP;
break; break;
case 443: case 443:
protocol = Protocol.HTTPS; protocol = Protocol.HTTPS;
break; break;
default: default:
protocol = Protocol.HTTP; protocol = Protocol.HTTP;
break; break;
} }
if (ip == null) { if (ip == null) {
if (client instanceof TerremarkVCloudExpressClient) { if (client instanceof TerremarkVCloudExpressClient) {
is = TerremarkVCloudExpressClient.class.cast(client).addInternetServiceToVDC( is = TerremarkVCloudExpressClient.class.cast(client).addInternetServiceToVDC(
vApp.getVDC().getHref(), vApp.getVDC().getHref(),
vApp.getName() + "-" + port, vApp.getName() + "-" + port,
protocol, protocol,
port, port,
withDescription(String.format("port %d access to serverId: %s name: %s", port, vApp.getName(), withDescription(String.format("port %d access to serverId: %s name: %s", port, vApp.getName(),
vApp.getName()))); vApp.getName())));
ip = is.getPublicIpAddress(); ip = is.getPublicIpAddress();
} else { } else {
logger.debug(">> creating InternetService in vDC %s:%s:%d", vApp.getVDC().getName(), protocol, port); logger.debug(">> creating InternetService in vDC %s:%s:%d", vApp.getVDC().getName(), protocol, port);
ip = TerremarkECloudClient.class.cast(client).activatePublicIpInVDC(vApp.getVDC().getHref()); // http://support.theenterprisecloud.com/kb/default.asp?id=706&Lang=1&SID=
// response with a 500 error code means we should look for an existing public ip to
// use
try {
ip = TerremarkECloudClient.class.cast(client).activatePublicIpInVDC(vApp.getVDC().getHref());
} catch (HttpResponseException e) {
if (e.getResponse().getStatusCode() == 500) {
logger.warn(">> no more ip addresses available, looking for one to re-use");
for (PublicIpAddress existingIp : client.getPublicIpsAssociatedWithVDC(vApp.getVDC().getHref())) {
Set<InternetService> services = client.getInternetServicesOnPublicIp(existingIp.getId());
if (services.size() == 0) {
ip = existingIp;
break;
}
}
if (ip == null)
throw e;
} else {
throw e;
}
}
is = client.addInternetServiceToExistingIp(ip.getId(), vApp.getName() + "-" + port, protocol, port, is = client.addInternetServiceToExistingIp(ip.getId(), vApp.getName() + "-" + port, protocol, port,
withDescription(String.format("port %d access to serverId: %s name: %s", port, vApp.getName(), withDescription(String.format("port %d access to serverId: %s name: %s", port, vApp.getName(),
vApp.getName()))); vApp.getName())));
} }
} else { } else {
logger.debug(">> adding InternetService %s:%s:%d", ip.getAddress(), protocol, port); logger.debug(">> adding InternetService %s:%s:%d", ip.getAddress(), protocol, port);
is = client.addInternetServiceToExistingIp( is = client.addInternetServiceToExistingIp(ip.getId(), vApp.getName() + "-" + port, protocol, port,
ip.getId(), withDescription(String.format("port %d access to serverId: %s name: %s", port, vApp.getName(),
vApp.getName() + "-" + port, vApp.getName())));
protocol,
port,
withDescription(String.format("port %d access to serverId: %s name: %s", port, vApp.getName(),
vApp.getName())));
} }
logger.debug("<< created InternetService(%s) %s:%s:%d", is.getName(), is.getPublicIpAddress().getAddress(), logger.debug("<< created InternetService(%s) %s:%s:%d", is.getName(), is.getPublicIpAddress().getAddress(), is
is.getProtocol(), is.getPort()); .getProtocol(), is.getPort());
logger.debug(">> adding Node %s:%d -> %s:%d", is.getPublicIpAddress().getAddress(), is.getPort(), logger.debug(">> adding Node %s:%d -> %s:%d", is.getPublicIpAddress().getAddress(), is.getPort(),
privateAddress, port); privateAddress, port);
Node node = client.addNode(is.getId(), privateAddress, vApp.getName() + "-" + port, port); Node node = client.addNode(is.getId(), privateAddress, vApp.getName() + "-" + port, port);
logger.debug("<< added Node(%s)", node.getName()); logger.debug("<< added Node(%s)", node.getName());
} }
@ -174,13 +192,13 @@ public class TerremarkVCloudComputeClient extends VCloudExpressComputeClientImpl
if (vApp.getNetworkToAddresses().containsValue(node.getIpAddress())) { if (vApp.getNetworkToAddresses().containsValue(node.getIpAddress())) {
ipAddresses.add(service.getPublicIpAddress()); ipAddresses.add(service.getPublicIpAddress());
logger.debug(">> deleting Node(%s) %s:%d -> %s:%d", node.getName(), service.getPublicIpAddress() logger.debug(">> deleting Node(%s) %s:%d -> %s:%d", node.getName(), service.getPublicIpAddress()
.getAddress(), service.getPort(), node.getIpAddress(), node.getPort()); .getAddress(), service.getPort(), node.getIpAddress(), node.getPort());
client.deleteNode(node.getId()); client.deleteNode(node.getId());
logger.debug("<< deleted Node(%s)", node.getName()); logger.debug("<< deleted Node(%s)", node.getName());
Set<Node> nodes = client.getNodes(service.getId()); Set<Node> nodes = client.getNodes(service.getId());
if (nodes.size() == 0) { if (nodes.size() == 0) {
logger.debug(">> deleting InternetService(%s) %s:%d", service.getName(), service.getPublicIpAddress() logger.debug(">> deleting InternetService(%s) %s:%d", service.getName(), service.getPublicIpAddress()
.getAddress(), service.getPort()); .getAddress(), service.getPort());
client.deleteInternetService(service.getId()); client.deleteInternetService(service.getId());
logger.debug("<< deleted InternetService(%s)", service.getName()); logger.debug("<< deleted InternetService(%s)", service.getName());
continue SERVICE; continue SERVICE;

View File

@ -32,7 +32,7 @@ import org.jclouds.compute.reference.ComputeServiceConstants;
import org.jclouds.http.HttpResponseException; import org.jclouds.http.HttpResponseException;
import org.jclouds.logging.Logger; import org.jclouds.logging.Logger;
import org.jclouds.util.Utils; import org.jclouds.util.Utils;
import org.jclouds.vcloud.terremark.TerremarkVCloudExpressClient; import org.jclouds.vcloud.terremark.TerremarkVCloudClient;
import org.jclouds.vcloud.terremark.compute.domain.OrgAndName; import org.jclouds.vcloud.terremark.compute.domain.OrgAndName;
import org.jclouds.vcloud.terremark.domain.KeyPair; import org.jclouds.vcloud.terremark.domain.KeyPair;
@ -48,11 +48,11 @@ public class CreateUniqueKeyPair implements Function<OrgAndName, KeyPair> {
@Resource @Resource
@Named(ComputeServiceConstants.COMPUTE_LOGGER) @Named(ComputeServiceConstants.COMPUTE_LOGGER)
protected Logger logger = Logger.NULL; protected Logger logger = Logger.NULL;
protected final TerremarkVCloudExpressClient trmkClient; protected final TerremarkVCloudClient trmkClient;
protected Supplier<String> randomSuffix; protected Supplier<String> randomSuffix;
@Inject @Inject
CreateUniqueKeyPair(TerremarkVCloudExpressClient trmkClient, Supplier<String> randomSuffix) { CreateUniqueKeyPair(TerremarkVCloudClient trmkClient, Supplier<String> randomSuffix) {
this.trmkClient = trmkClient; this.trmkClient = trmkClient;
this.randomSuffix = randomSuffix; this.randomSuffix = randomSuffix;
} }

View File

@ -28,7 +28,7 @@ import javax.inject.Singleton;
import org.jclouds.compute.reference.ComputeServiceConstants; import org.jclouds.compute.reference.ComputeServiceConstants;
import org.jclouds.logging.Logger; import org.jclouds.logging.Logger;
import org.jclouds.vcloud.terremark.TerremarkVCloudExpressClient; import org.jclouds.vcloud.terremark.TerremarkVCloudClient;
import org.jclouds.vcloud.terremark.compute.domain.KeyPairCredentials; import org.jclouds.vcloud.terremark.compute.domain.KeyPairCredentials;
import org.jclouds.vcloud.terremark.compute.domain.OrgAndName; import org.jclouds.vcloud.terremark.compute.domain.OrgAndName;
import org.jclouds.vcloud.terremark.domain.KeyPair; import org.jclouds.vcloud.terremark.domain.KeyPair;
@ -44,12 +44,11 @@ public class DeleteKeyPair {
@Named(ComputeServiceConstants.COMPUTE_LOGGER) @Named(ComputeServiceConstants.COMPUTE_LOGGER)
protected Logger logger = Logger.NULL; protected Logger logger = Logger.NULL;
final TerremarkVCloudExpressClient terremarkClient; final TerremarkVCloudClient terremarkClient;
final ConcurrentMap<OrgAndName, KeyPairCredentials> credentialsMap; final ConcurrentMap<OrgAndName, KeyPairCredentials> credentialsMap;
@Inject @Inject
DeleteKeyPair(TerremarkVCloudExpressClient terremarkClient, DeleteKeyPair(TerremarkVCloudClient terremarkClient, ConcurrentMap<OrgAndName, KeyPairCredentials> credentialsMap) {
ConcurrentMap<OrgAndName, KeyPairCredentials> credentialsMap) {
this.terremarkClient = terremarkClient; this.terremarkClient = terremarkClient;
this.credentialsMap = credentialsMap; this.credentialsMap = credentialsMap;
} }

View File

@ -25,10 +25,14 @@ import static com.google.common.base.Preconditions.checkNotNull;
import java.util.regex.Matcher; import java.util.regex.Matcher;
import java.util.regex.Pattern; import java.util.regex.Pattern;
import javax.annotation.Resource;
import javax.inject.Named;
import javax.inject.Singleton; import javax.inject.Singleton;
import org.jclouds.compute.reference.ComputeServiceConstants;
import org.jclouds.compute.strategy.PopulateDefaultLoginCredentialsForImageStrategy; import org.jclouds.compute.strategy.PopulateDefaultLoginCredentialsForImageStrategy;
import org.jclouds.domain.Credentials; import org.jclouds.domain.Credentials;
import org.jclouds.logging.Logger;
import org.jclouds.vcloud.domain.VCloudExpressVAppTemplate; import org.jclouds.vcloud.domain.VCloudExpressVAppTemplate;
/** /**
@ -36,15 +40,20 @@ import org.jclouds.vcloud.domain.VCloudExpressVAppTemplate;
*/ */
@Singleton @Singleton
public class ParseVAppTemplateDescriptionToGetDefaultLoginCredentials implements public class ParseVAppTemplateDescriptionToGetDefaultLoginCredentials implements
PopulateDefaultLoginCredentialsForImageStrategy { PopulateDefaultLoginCredentialsForImageStrategy {
@Resource
@Named(ComputeServiceConstants.COMPUTE_LOGGER)
protected Logger logger = Logger.NULL;
public static final Pattern USER_PASSWORD_PATTERN = Pattern public static final Pattern USER_PASSWORD_PATTERN = Pattern
.compile(".*[Uu]sername: ([a-z]+) ?.*\n[Pp]assword: ([^ \n\r]+) ?\r?\n.*"); .compile(".*[Uu]sername: ([a-z]+) ?.*\n[Pp]assword: ([^ \n\r]+) ?\r?\n.*");
@Override @Override
public Credentials execute(Object resourceToAuthenticate) { public Credentials execute(Object resourceToAuthenticate) {
checkNotNull(resourceToAuthenticate); checkNotNull(resourceToAuthenticate);
checkArgument(resourceToAuthenticate instanceof VCloudExpressVAppTemplate, "Resource must be an VAppTemplate (for Terremark)"); checkArgument(resourceToAuthenticate instanceof VCloudExpressVAppTemplate,
"Resource must be an VAppTemplate (for Terremark)");
VCloudExpressVAppTemplate template = (VCloudExpressVAppTemplate) resourceToAuthenticate; VCloudExpressVAppTemplate template = (VCloudExpressVAppTemplate) resourceToAuthenticate;
String search = template.getDescription() != null ? template.getDescription() : template.getName(); String search = template.getDescription() != null ? template.getDescription() : template.getName();
if (search.indexOf("Windows") >= 0) { if (search.indexOf("Windows") >= 0) {
@ -54,8 +63,9 @@ public class ParseVAppTemplateDescriptionToGetDefaultLoginCredentials implements
if (matcher.find()) { if (matcher.find()) {
return new Credentials(matcher.group(1), matcher.group(2)); return new Credentials(matcher.group(1), matcher.group(2));
} else { } else {
throw new RuntimeException("could not parse username/password for image: " + template.getHref() + "\n" logger.warn("could not parse username/password for image: " + template.getHref() + "\n"
+ search); + search);
return null;
} }
} }
} }

View File

@ -19,17 +19,27 @@
package org.jclouds.vcloud.terremark.config; package org.jclouds.vcloud.terremark.config;
import java.net.URI;
import java.util.Map;
import java.util.NoSuchElementException;
import javax.inject.Singleton; import javax.inject.Singleton;
import org.jclouds.http.RequiresHttp; import org.jclouds.http.RequiresHttp;
import org.jclouds.rest.ConfiguresRestClient; import org.jclouds.rest.ConfiguresRestClient;
import org.jclouds.rest.ResourceNotFoundException;
import org.jclouds.vcloud.VCloudExpressAsyncClient; import org.jclouds.vcloud.VCloudExpressAsyncClient;
import org.jclouds.vcloud.VCloudExpressClient; import org.jclouds.vcloud.VCloudExpressClient;
import org.jclouds.vcloud.terremark.TerremarkVCloudAsyncClient; import org.jclouds.vcloud.domain.ReferenceType;
import org.jclouds.vcloud.terremark.TerremarkVCloudClient; import org.jclouds.vcloud.domain.network.OrgNetwork;
import org.jclouds.vcloud.terremark.TerremarkECloudAsyncClient; import org.jclouds.vcloud.terremark.TerremarkECloudAsyncClient;
import org.jclouds.vcloud.terremark.TerremarkECloudClient; import org.jclouds.vcloud.terremark.TerremarkECloudClient;
import org.jclouds.vcloud.terremark.TerremarkVCloudAsyncClient;
import org.jclouds.vcloud.terremark.TerremarkVCloudClient;
import com.google.common.base.Predicate;
import com.google.common.collect.Iterables;
import com.google.inject.Injector;
import com.google.inject.Provides; import com.google.inject.Provides;
/** /**
@ -70,4 +80,31 @@ public class TerremarkECloudRestClientModule extends
return in; return in;
} }
@Override
protected URI findDefaultNetworkForVDC(org.jclouds.vcloud.domain.VDC vDC, Map<String, ReferenceType> networks,
final Injector injector) {
// TODO FIXME XXX: In Terremark Enterprise environment with multiple VDC's this does not
// work well.
// Each VDC will have differnt network subnets. So we cannot assume the default VDC's
// networks will
// work with non-default VDC's. So make PROPERTY_VCLOUD_DEFAULT_NETWORK optional. If
// this property
// is not set, they are expected to add NetworkConfig to the options when launching a
// server.
logger.warn("default network for vdc %s not set", vDC.getName());
try {
return Iterables.find(networks.values(), new Predicate<ReferenceType>() {
@Override
public boolean apply(ReferenceType input) {
OrgNetwork network = injector.getInstance(TerremarkECloudClient.class).getNetwork(input.getHref());
// TODO: get extension data on this network and check NetworkType == DMZ
return network.getDescription() != null &&network.getDescription().toLowerCase().contains("dmz");
}
}).getHref();
} catch (NoSuchElementException e) {
throw new ResourceNotFoundException("no dmz networks in vdc " + vDC.getName() + ": " + networks);
}
}
} }

View File

@ -54,10 +54,11 @@ public class ParseTerremarkVCloudErrorFromHttpResponse implements HttpErrorHandl
try { try {
String content = parseErrorFromContentOrNull(command, response); String content = parseErrorFromContentOrNull(command, response);
if (response.getMessage() != null && ((response.getMessage().indexOf("because there is a pending task running") != -1) if (response.getMessage() != null
|| (response.getMessage().indexOf("because it is already powered off") != -1) && ((response.getMessage().indexOf("because there is a pending task running") != -1)
|| (response.getMessage().indexOf("already exists") != -1) || (response.getMessage().indexOf("because it is already powered off") != -1)
|| (response.getMessage().indexOf("same name exists") != -1))) || (response.getMessage().indexOf("already exists") != -1) || (response.getMessage()
.indexOf("same name exists") != -1)))
exception = new IllegalStateException(response.getMessage(), exception); exception = new IllegalStateException(response.getMessage(), exception);
else else
switch (response.getStatusCode()) { switch (response.getStatusCode()) {
@ -80,8 +81,9 @@ public class ParseTerremarkVCloudErrorFromHttpResponse implements HttpErrorHandl
} }
exception = new ResourceNotFoundException(message, exception); exception = new ResourceNotFoundException(message, exception);
break; break;
default: case 501:
exception = new HttpResponseException(command, response, content); if (response.getMessage() != null && (response.getMessage().indexOf("NotImplemented") != -1))
exception = new UnsupportedOperationException(response.getMessage(), exception);
} }
} finally { } finally {
releasePayload(response); releasePayload(response);

View File

@ -51,8 +51,8 @@ import org.jclouds.util.Utils;
import org.jclouds.vcloud.CommonVCloudClient; import org.jclouds.vcloud.CommonVCloudClient;
import org.jclouds.vcloud.VCloudExpressAsyncClientTest.VCloudRestClientModuleExtension.TestOrgCatalogItemSupplier; import org.jclouds.vcloud.VCloudExpressAsyncClientTest.VCloudRestClientModuleExtension.TestOrgCatalogItemSupplier;
import org.jclouds.vcloud.VCloudExpressAsyncClientTest.VCloudRestClientModuleExtension.TestOrgCatalogSupplier; import org.jclouds.vcloud.VCloudExpressAsyncClientTest.VCloudRestClientModuleExtension.TestOrgCatalogSupplier;
import org.jclouds.vcloud.domain.ReferenceType;
import org.jclouds.vcloud.domain.Org; import org.jclouds.vcloud.domain.Org;
import org.jclouds.vcloud.domain.ReferenceType;
import org.jclouds.vcloud.domain.VCloudSession; import org.jclouds.vcloud.domain.VCloudSession;
import org.jclouds.vcloud.domain.internal.ReferenceTypeImpl; import org.jclouds.vcloud.domain.internal.ReferenceTypeImpl;
import org.jclouds.vcloud.domain.network.NetworkConfig; import org.jclouds.vcloud.domain.network.NetworkConfig;
@ -604,7 +604,7 @@ public class TerremarkECloudAsyncClientTest extends RestClientTest<TerremarkEClo
} }
@Override @Override
protected URI provideDefaultNetwork(URI vdc, CommonVCloudClient client, Injector injector) { protected URI provideDefaultNetwork(URI vdc, Injector injector) {
return URI.create("https://vcloud.safesecureweb.com/network/1990"); return URI.create("https://vcloud.safesecureweb.com/network/1990");
} }
} }

View File

@ -745,7 +745,7 @@ public class TerremarkVCloudExpressAsyncClientTest extends RestClientTest<Terrem
} }
@Override @Override
protected URI provideDefaultNetwork(URI vdc, CommonVCloudClient client, Injector injector) { protected URI provideDefaultNetwork(URI vdc, Injector injector) {
return URI.create("https://vcloud.safesecureweb.com/network/1990"); return URI.create("https://vcloud.safesecureweb.com/network/1990");
} }
} }

View File

@ -33,8 +33,10 @@ import org.jclouds.compute.domain.Template;
import org.jclouds.compute.domain.TemplateBuilder; import org.jclouds.compute.domain.TemplateBuilder;
import org.jclouds.rest.RestContext; import org.jclouds.rest.RestContext;
import org.jclouds.ssh.jsch.config.JschSshClientModule; import org.jclouds.ssh.jsch.config.JschSshClientModule;
import org.jclouds.vcloud.domain.VCloudExpressVApp;
import org.jclouds.vcloud.terremark.TerremarkECloudAsyncClient; import org.jclouds.vcloud.terremark.TerremarkECloudAsyncClient;
import org.jclouds.vcloud.terremark.TerremarkECloudClient; import org.jclouds.vcloud.terremark.TerremarkECloudClient;
import org.jclouds.vcloud.terremark.TerremarkVCloudClient;
import org.testng.annotations.Test; import org.testng.annotations.Test;
/** /**
@ -50,13 +52,14 @@ public class TerremarkECloudComputeServiceLiveTestDisabled extends BaseComputeSe
@Override @Override
public void setServiceDefaults() { public void setServiceDefaults() {
tag = "trmke"; tag = "te";
} }
@Test @Test
public void testTemplateBuilder() { public void testTemplateBuilder() {
Template defaultTemplate = client.templateBuilder().build(); Template defaultTemplate = client.templateBuilder().build();
assertEquals(defaultTemplate.getImage().getOperatingSystem().is64Bit(), false); assertEquals(defaultTemplate.getImage().getOperatingSystem().is64Bit(), true);
assertEquals(defaultTemplate.getImage().getOperatingSystem().getVersion(), "10.04");
assertEquals(defaultTemplate.getImage().getOperatingSystem().getFamily(), OsFamily.UBUNTU); assertEquals(defaultTemplate.getImage().getOperatingSystem().getFamily(), OsFamily.UBUNTU);
assert defaultTemplate.getLocation().getDescription() != null;// different per org assert defaultTemplate.getLocation().getDescription() != null;// different per org
assertEquals(getCores(defaultTemplate.getHardware()), 1.0d); assertEquals(getCores(defaultTemplate.getHardware()), 1.0d);
@ -90,7 +93,8 @@ public class TerremarkECloudComputeServiceLiveTestDisabled extends BaseComputeSe
assert image.getProviderId() != null : image; assert image.getProviderId() != null : image;
// image.getLocationId() can be null, if it is a location-free image // image.getLocationId() can be null, if it is a location-free image
assertEquals(image.getType(), ComputeType.IMAGE); assertEquals(image.getType(), ComputeType.IMAGE);
if (image.getOperatingSystem().getFamily() != OsFamily.WINDOWS) { if (image.getOperatingSystem().getFamily() != OsFamily.WINDOWS
&& image.getOperatingSystem().getFamily() != OsFamily.SOLARIS) {
assert image.getDefaultCredentials() != null && image.getDefaultCredentials().identity != null : image; assert image.getDefaultCredentials() != null && image.getDefaultCredentials().identity != null : image;
assert image.getDefaultCredentials().credential != null : image; assert image.getDefaultCredentials().credential != null : image;
} }
@ -105,9 +109,18 @@ public class TerremarkECloudComputeServiceLiveTestDisabled extends BaseComputeSe
assertEquals(node.getType(), ComputeType.NODE); assertEquals(node.getType(), ComputeType.NODE);
NodeMetadata allData = client.getNodeMetadata(node.getId()); NodeMetadata allData = client.getNodeMetadata(node.getId());
System.out.println(allData.getHardware()); System.out.println(allData.getHardware());
RestContext<TerremarkVCloudClient, TerremarkVCloudClient> tmContext = new ComputeServiceContextFactory()
.createContext(provider, identity, credential).getProviderSpecificContext();
VCloudExpressVApp vApp = tmContext.getApi().findVAppInOrgVDCNamed(null, null, allData.getName());
assertEquals(vApp.getName(), allData.getName());
} }
} }
@Override
public void testDestroyNodes() {
super.testDestroyNodes();
}
@Override @Override
protected JschSshClientModule getSshModule() { protected JschSshClientModule getSshModule() {
return new JschSshClientModule(); return new JschSshClientModule();

View File

@ -34,6 +34,7 @@ import org.jclouds.compute.domain.TemplateBuilder;
import org.jclouds.rest.RestContext; import org.jclouds.rest.RestContext;
import org.jclouds.ssh.jsch.config.JschSshClientModule; import org.jclouds.ssh.jsch.config.JschSshClientModule;
import org.jclouds.vcloud.domain.VCloudExpressVApp; import org.jclouds.vcloud.domain.VCloudExpressVApp;
import org.jclouds.vcloud.terremark.TerremarkVCloudClient;
import org.jclouds.vcloud.terremark.TerremarkVCloudExpressAsyncClient; import org.jclouds.vcloud.terremark.TerremarkVCloudExpressAsyncClient;
import org.jclouds.vcloud.terremark.TerremarkVCloudExpressClient; import org.jclouds.vcloud.terremark.TerremarkVCloudExpressClient;
import org.testng.annotations.Test; import org.testng.annotations.Test;
@ -105,13 +106,18 @@ public class TerremarkVCloudExpressComputeServiceLiveTest extends BaseComputeSer
assertEquals(node.getType(), ComputeType.NODE); assertEquals(node.getType(), ComputeType.NODE);
NodeMetadata allData = client.getNodeMetadata(node.getId()); NodeMetadata allData = client.getNodeMetadata(node.getId());
System.out.println(allData.getHardware()); System.out.println(allData.getHardware());
RestContext<TerremarkVCloudExpressClient, TerremarkVCloudExpressAsyncClient> tmContext = new ComputeServiceContextFactory() RestContext<TerremarkVCloudClient, TerremarkVCloudClient> tmContext = new ComputeServiceContextFactory()
.createContext(provider, identity, credential).getProviderSpecificContext(); .createContext(provider, identity, credential).getProviderSpecificContext();
VCloudExpressVApp vApp = tmContext.getApi().findVAppInOrgVDCNamed(null, null, allData.getName()); VCloudExpressVApp vApp = tmContext.getApi().findVAppInOrgVDCNamed(null, null, allData.getName());
assertEquals(vApp.getName(), allData.getName()); assertEquals(vApp.getName(), allData.getName());
} }
} }
@Override
public void testDestroyNodes() {
super.testDestroyNodes();
}
@Override @Override
protected JschSshClientModule getSshModule() { protected JschSshClientModule getSshModule() {
return new JschSshClientModule(); return new JschSshClientModule();

View File

@ -81,7 +81,21 @@ public class PopulateDefaultLoginCredentialsForVAppTemplateTest {
assertEquals(creds.credential, "vpncubed"); assertEquals(creds.credential, "vpncubed");
verify(template); verify(template);
} }
@Test
public void testEC() throws IOException {
InputStream is = getClass().getResourceAsStream("/terremark/ec_description.txt");
String description = new String(ByteStreams.toByteArray(is));
VCloudExpressVAppTemplate template = createMock(VCloudExpressVAppTemplate.class);
expect(template.getDescription()).andReturn(description).atLeastOnce();
replay(template);
ParseVAppTemplateDescriptionToGetDefaultLoginCredentials converter = new ParseVAppTemplateDescriptionToGetDefaultLoginCredentials();
Credentials creds = converter.execute(template);
assertEquals(creds.identity, "ecloud");
assertEquals(creds.credential, "TmrkCl0ud1s#1!");
verify(template);
}
@Test @Test
public void testWindows() throws IOException { public void testWindows() throws IOException {
InputStream is = getClass().getResourceAsStream("/terremark/windows_description.txt"); InputStream is = getClass().getResourceAsStream("/terremark/windows_description.txt");

View File

@ -71,6 +71,13 @@ public class ParseTerremarkVCloudErrorFromHttpResponseTest extends BaseHttpError
"", "", AuthorizationException.class); "", "", AuthorizationException.class);
} }
@Test
public void test501SetsNotImplementedMakesUnsupportedOperationException() {
assertCodeMakes("POST", URI
.create("https://services.enterprisecloud.terremark.com/api/v0.8b-ext2.5/vapp/49373/action/undeploy"),
501, "HTTP/1.1 501 NotImplemented", "", UnsupportedOperationException.class);
}
@Test @Test
public void testbecause_there_is_a_pending_task_runningSetsIllegalStateException() { public void testbecause_there_is_a_pending_task_runningSetsIllegalStateException() {
assertCodeMakes("GET", URI.create("https://services.vcloudexpress.terremark.com/api/v0.8a-ext1.6/vdc/32"), 500, assertCodeMakes("GET", URI.create("https://services.vcloudexpress.terremark.com/api/v0.8a-ext1.6/vdc/32"), 500,

View File

@ -0,0 +1,6 @@
username: ecloud
password: TmrkCl0ud1s#1!
This template consists of a base Ubuntu Server 10.04 installation. Additional software is available via apt. Updates are available via Software Updater.
The hostname and base IP will be set as part of the server creation process based on user input.