|
|
|
@ -69,8 +69,6 @@ import java.util.concurrent.TimeUnit;
|
|
|
|
|
import java.util.concurrent.TimeoutException;
|
|
|
|
|
import java.util.logging.Logger;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
import com.microsoft.windowsazure.Configuration;
|
|
|
|
|
import com.microsoft.windowsazure.exception.ServiceException;
|
|
|
|
|
import com.microsoft.azure.exceptions.AzureCloudException;
|
|
|
|
@ -111,13 +109,13 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
private static final Logger LOGGER = Logger.getLogger(AzureVMManagementServiceDelegate.class.getName());
|
|
|
|
|
|
|
|
|
|
private static final String EMBEDDED_TEMPLATE_FILENAME = "/referenceImageTemplate.json";
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private static final String EMBEDDED_TEMPLATE_WITH_SCRIPT_FILENAME = "/referenceImageTemplateWithScript.json";
|
|
|
|
|
|
|
|
|
|
private static final String EMBEDDED_TEMPLATE_IMAGE_FILENAME = "/customImageTemplate.json";
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private static final String EMBEDDED_TEMPLATE_IMAGE_WITH_SCRIPT_FILENAME = "/customImageTemplateWithScript.json";
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private static final String VIRTUAL_NETWORK_TEMPLATE_FRAGMENT_FILENAME = "/virtualNetworkFragment.json";
|
|
|
|
|
|
|
|
|
|
private static final String IMAGE_CUSTOM_REFERENCE = "custom";
|
|
|
|
@ -127,15 +125,16 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
private static final Map<String, String> AVAILABLE_LOCATIONS_STD = getAvailableLocationsStandard();
|
|
|
|
|
|
|
|
|
|
private static final Map<String, String> AVAILABLE_LOCATIONS_CHINA = getAvailableLocationsChina();
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private static final Map<String, String> AVAILABLE_LOCATIONS_ALL = getAvailableLocationsAll();
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Creates a new deployment of VMs based on the provided template
|
|
|
|
|
*
|
|
|
|
|
* @param template Template to deploy
|
|
|
|
|
* @param numberOfAgents Number of agents to create
|
|
|
|
|
* @return The base name for the VMs that were created
|
|
|
|
|
* @throws AzureCloudException
|
|
|
|
|
* @throws AzureCloudException
|
|
|
|
|
*/
|
|
|
|
|
public static AzureVMDeploymentInfo createDeployment(final AzureVMAgentTemplate template, final int numberOfAgents)
|
|
|
|
|
throws AzureCloudException {
|
|
|
|
@ -151,47 +150,50 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
final String deploymentName = AzureUtil.getDeploymentName(template.getTemplateName(), timestamp);
|
|
|
|
|
final String vmBaseName = AzureUtil.getVMBaseName(template.getTemplateName(), deploymentName, template.getOsType(), numberOfAgents);
|
|
|
|
|
final String locationName = getLocationName(template.getLocation());
|
|
|
|
|
if (!template.getResourceGroupName().matches(Constants.DEFAULT_RESOURCE_GROUP_PATTERN)) {
|
|
|
|
|
LOGGER.log(Level.SEVERE,
|
|
|
|
|
"AzureVMManagementServiceDelegate: createDeployment: ResourceGroup Name {0} is invalid. It should be 1-64 alphanumeric characters",
|
|
|
|
|
new Object[]{template.getResourceGroupName()});
|
|
|
|
|
throw new Exception("ResourceGroup Name is invalid");
|
|
|
|
|
}
|
|
|
|
|
final String resourceGroupName = template.getResourceGroupName();
|
|
|
|
|
LOGGER.log(Level.INFO,
|
|
|
|
|
"AzureVMManagementServiceDelegate: createDeployment: Creating a new deployment {0} with VM base name {1}",
|
|
|
|
|
new Object[] { deploymentName, vmBaseName} );
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
new Object[]{deploymentName, vmBaseName});
|
|
|
|
|
|
|
|
|
|
client.getResourceGroupsOperations().createOrUpdate(
|
|
|
|
|
resourceGroupName,
|
|
|
|
|
new ResourceGroup(locationName));
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
final Deployment deployment = new Deployment();
|
|
|
|
|
final DeploymentProperties properties = new DeploymentProperties();
|
|
|
|
|
deployment.setProperties(properties);
|
|
|
|
|
|
|
|
|
|
final InputStream embeddedTemplate;
|
|
|
|
|
final boolean useCustomScriptExtension =
|
|
|
|
|
template.getOsType().equals(Constants.OS_TYPE_WINDOWS) && !StringUtils.isBlank(template.getInitScript()) &&
|
|
|
|
|
template.getAgentLaunchMethod().equals(Constants.LAUNCH_METHOD_JNLP);
|
|
|
|
|
final boolean useCustomScriptExtension
|
|
|
|
|
= template.getOsType().equals(Constants.OS_TYPE_WINDOWS) && !StringUtils.isBlank(template.getInitScript())
|
|
|
|
|
&& template.getAgentLaunchMethod().equals(Constants.LAUNCH_METHOD_JNLP);
|
|
|
|
|
|
|
|
|
|
// check if a custom image id has been provided otherwise work with publisher and offer
|
|
|
|
|
if (template.getImageReferenceType().equals(IMAGE_CUSTOM_REFERENCE)) {
|
|
|
|
|
if (useCustomScriptExtension) {
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: createDeployment: Use embedded deployment template {0}", EMBEDDED_TEMPLATE_IMAGE_WITH_SCRIPT_FILENAME);
|
|
|
|
|
embeddedTemplate
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(EMBEDDED_TEMPLATE_IMAGE_WITH_SCRIPT_FILENAME);
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(EMBEDDED_TEMPLATE_IMAGE_WITH_SCRIPT_FILENAME);
|
|
|
|
|
} else {
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: createDeployment: Use embedded deployment template (with script) {0}", EMBEDDED_TEMPLATE_IMAGE_FILENAME);
|
|
|
|
|
embeddedTemplate
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(EMBEDDED_TEMPLATE_IMAGE_FILENAME);
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(EMBEDDED_TEMPLATE_IMAGE_FILENAME);
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
if (useCustomScriptExtension) {
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: createDeployment: Use embedded deployment template (with script) {0}", EMBEDDED_TEMPLATE_WITH_SCRIPT_FILENAME);
|
|
|
|
|
embeddedTemplate
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(EMBEDDED_TEMPLATE_WITH_SCRIPT_FILENAME);
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(EMBEDDED_TEMPLATE_WITH_SCRIPT_FILENAME);
|
|
|
|
|
} else {
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: createDeployment: Use embedded deployment template {0}", EMBEDDED_TEMPLATE_FILENAME);
|
|
|
|
|
embeddedTemplate
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(EMBEDDED_TEMPLATE_FILENAME);
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(EMBEDDED_TEMPLATE_FILENAME);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -203,7 +205,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
count.put("type", "int");
|
|
|
|
|
count.put("defaultValue", numberOfAgents);
|
|
|
|
|
ObjectNode.class.cast(tmp.get("parameters")).replace("count", count);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("vmName", vmBaseName);
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("location", locationName);
|
|
|
|
|
|
|
|
|
@ -226,7 +228,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
if (StringUtils.isNotBlank(template.getImage())) {
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("image", template.getImage());
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// If using the custom script extension (vs. SSH) to startup the powershell scripts,
|
|
|
|
|
// add variables for that and upload the init script to the storage account
|
|
|
|
|
if (useCustomScriptExtension) {
|
|
|
|
@ -235,14 +237,14 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
ArrayNode clientSecretsNode = ObjectNode.class.cast(tmp.get("variables")).putArray("clientSecrets");
|
|
|
|
|
for (int i = 0; i < numberOfAgents; i++) {
|
|
|
|
|
clientSecretsNode.add(
|
|
|
|
|
JnlpSlaveAgentProtocol.SLAVE_SECRET.mac(String.format("%s%d", vmBaseName, i)));
|
|
|
|
|
JnlpSlaveAgentProtocol.SLAVE_SECRET.mac(String.format("%s%d", vmBaseName, i)));
|
|
|
|
|
}
|
|
|
|
|
// Upload the startup script to blob storage
|
|
|
|
|
String scriptName = String.format("%s%s", deploymentName, "init.ps1");
|
|
|
|
|
String scriptUri = uploadCustomScript(template, scriptName);
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("startupScriptURI", scriptUri);
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("startupScriptName", scriptName);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
String storageAccountKey = ServiceDelegateHelper.getStorageManagementClient(config).getStorageAccountsOperations().listKeys(
|
|
|
|
|
template.getResourceGroupName(), template.getStorageAccountName())
|
|
|
|
|
.getStorageAccountKeys().getKey1();
|
|
|
|
@ -250,7 +252,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
final ObjectNode storageAccountKeyNode = mapper.createObjectNode();
|
|
|
|
|
storageAccountKeyNode.put("type", "secureString");
|
|
|
|
|
storageAccountKeyNode.put("defaultValue", storageAccountKey);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Add the storage account key
|
|
|
|
|
ObjectNode.class.cast(tmp.get("parameters")).replace("storageAccountKey", storageAccountKeyNode);
|
|
|
|
|
}
|
|
|
|
@ -258,7 +260,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("vmSize", template.getVirtualMachineSize());
|
|
|
|
|
// Grab the username/pass
|
|
|
|
|
StandardUsernamePasswordCredentials creds = AzureUtil.getCredentials(template.getCredentialsId());
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("adminUsername", creds.getUsername());
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("adminPassword", creds.getPassword().getPlainText());
|
|
|
|
|
|
|
|
|
@ -271,29 +273,28 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
if (StringUtils.isNotBlank(template.getVirtualNetworkName())) {
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("virtualNetworkName", template.getVirtualNetworkName());
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("subnetName", template.getSubnetName());
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
} else {
|
|
|
|
|
// Add the definition of the vnet and subnet into the template
|
|
|
|
|
final String virtualNetworkName = Constants.DEFAULT_VNET_NAME;
|
|
|
|
|
final String subnetName = Constants.DEFAULT_SUBNET_NAME;
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("virtualNetworkName", virtualNetworkName);
|
|
|
|
|
ObjectNode.class.cast(tmp.get("variables")).put("subnetName", subnetName);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Read the vnet fragment
|
|
|
|
|
InputStream fragmentStream =
|
|
|
|
|
AzureVMManagementServiceDelegate.class.getResourceAsStream(VIRTUAL_NETWORK_TEMPLATE_FRAGMENT_FILENAME);
|
|
|
|
|
|
|
|
|
|
InputStream fragmentStream
|
|
|
|
|
= AzureVMManagementServiceDelegate.class.getResourceAsStream(VIRTUAL_NETWORK_TEMPLATE_FRAGMENT_FILENAME);
|
|
|
|
|
|
|
|
|
|
final JsonNode virtualNetworkFragment = mapper.readTree(fragmentStream);
|
|
|
|
|
// Add the virtual network fragment
|
|
|
|
|
ArrayNode.class.cast(tmp.get("resources")).add(virtualNetworkFragment);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Because we created/updated this in the template, we need to add the appropriate
|
|
|
|
|
// dependsOn node to the networkInterface
|
|
|
|
|
// Microsoft.Network/virtualNetworks/<vnet name>
|
|
|
|
|
// Find the network interfaces node
|
|
|
|
|
ArrayNode resourcesNodes = ArrayNode.class.cast(tmp.get("resources"));
|
|
|
|
|
Iterator<JsonNode> resourcesNodesIter = resourcesNodes.elements();
|
|
|
|
|
while(resourcesNodesIter.hasNext()) {
|
|
|
|
|
while (resourcesNodesIter.hasNext()) {
|
|
|
|
|
JsonNode resourcesNode = resourcesNodesIter.next();
|
|
|
|
|
JsonNode typeNode = resourcesNode.get("type");
|
|
|
|
|
if (typeNode == null || !typeNode.asText().equals("Microsoft.Network/networkInterfaces")) {
|
|
|
|
@ -315,7 +316,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
AzureVMAgentCleanUpTask.registerDeployment(template.getAzureCloud().name, template.getResourceGroupName(), deploymentName);
|
|
|
|
|
// Create the deployment
|
|
|
|
|
client.getDeploymentsOperations().createOrUpdate(template.getResourceGroupName(), deploymentName, deployment);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return new AzureVMDeploymentInfo(deploymentName, vmBaseName, numberOfAgents);
|
|
|
|
|
} catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.SEVERE, "AzureVMManagementServiceDelegate: deployment: Unable to deploy", e);
|
|
|
|
@ -324,9 +325,10 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
throw new AzureCloudException(e);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Uploads the custom script for a template to blob storage
|
|
|
|
|
*
|
|
|
|
|
* @param template Template containing script to upload
|
|
|
|
|
* @return URI of script
|
|
|
|
|
*/
|
|
|
|
@ -342,7 +344,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
final StorageManagementClient storageClient = ServiceDelegateHelper.getStorageManagementClient(config);
|
|
|
|
|
|
|
|
|
|
rmClient.getResourceGroupsOperations().createOrUpdate(resourceGroupName, new ResourceGroup(location));
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
StorageAccountCreateParameters createParams = new StorageAccountCreateParameters();
|
|
|
|
|
createParams.setLocation(location);
|
|
|
|
|
createParams.setAccountType(AccountType.StandardLRS);
|
|
|
|
@ -352,10 +354,10 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
String storageAccountKey = storageClient.getStorageAccountsOperations().listKeys(resourceGroupName, targetStorageAccount)
|
|
|
|
|
.getStorageAccountKeys().getKey1();
|
|
|
|
|
String scriptText = template.getInitScript();
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
String blobURL = StorageServiceDelegate.uploadFileToStorage(
|
|
|
|
|
config, targetStorageAccount, storageAccountKey,
|
|
|
|
|
storageClient.getBaseUri().toString(), resourceGroupName, Constants.CONFIG_CONTAINER_NAME,
|
|
|
|
|
storageClient.getBaseUri().toString(), resourceGroupName, Constants.CONFIG_CONTAINER_NAME,
|
|
|
|
|
targetScriptName, scriptText.getBytes("UTF-8"));
|
|
|
|
|
return blobURL;
|
|
|
|
|
}
|
|
|
|
@ -399,17 +401,18 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
azureAgent.setPublicDNSName(pubIP.getDnsSettings().getFqdn());
|
|
|
|
|
azureAgent.setSshPort(Constants.DEFAULT_SSH_PORT);
|
|
|
|
|
|
|
|
|
|
LOGGER.log(Level.INFO, "Azure agent details:\nnodeName{0}\nadminUserName={1}\nshutdownOnIdle={2}\nretentionTimeInMin={3}\nlabels={4}",
|
|
|
|
|
new Object[] { azureAgent.getNodeName(), azureAgent.getVMCredentialsId(), azureAgent.isShutdownOnIdle(),
|
|
|
|
|
azureAgent.getRetentionTimeInMin(), azureAgent.getLabelString()});
|
|
|
|
|
LOGGER.log(Level.INFO, "Azure agent details:\nnodeName{0}\nadminUserName={1}\nshutdownOnIdle={2}\nretentionTimeInMin={3}\nlabels={4}",
|
|
|
|
|
new Object[]{azureAgent.getNodeName(), azureAgent.getVMCredentialsId(), azureAgent.isShutdownOnIdle(),
|
|
|
|
|
azureAgent.getRetentionTimeInMin(), azureAgent.getLabelString()});
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Determines whether a virtual machine exists.
|
|
|
|
|
*
|
|
|
|
|
* @param configuration Configuration for the subscription
|
|
|
|
|
* @param vmName Name of the VM.
|
|
|
|
|
* @param resourceGroupName Resource group of the VM.
|
|
|
|
|
* @return
|
|
|
|
|
* @return
|
|
|
|
|
*/
|
|
|
|
|
private static boolean virtualMachineExists(final Configuration config, final String vmName, final String resourceGroupName) {
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: virtualMachineExists: check for {0}", vmName);
|
|
|
|
@ -434,6 +437,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Determines whether a given agent exists.
|
|
|
|
|
*
|
|
|
|
|
* @param agent to check
|
|
|
|
|
* @return True if the agent exists, false otherwise
|
|
|
|
|
*/
|
|
|
|
@ -441,10 +445,9 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
try {
|
|
|
|
|
Configuration config = ServiceDelegateHelper.getConfiguration(agent);
|
|
|
|
|
return virtualMachineExists(config, agent.getNodeName(), agent.getResourceGroupName());
|
|
|
|
|
}
|
|
|
|
|
catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.INFO,
|
|
|
|
|
"AzureVMManagementServiceDelegate: virtualMachineExists: error while determining whether vm exists", e);
|
|
|
|
|
} catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.INFO,
|
|
|
|
|
"AzureVMManagementServiceDelegate: virtualMachineExists: error while determining whether vm exists", e);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
@ -470,7 +473,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
+ "\tfound agent {0}\n"
|
|
|
|
|
+ "\tOS type {1}\n"
|
|
|
|
|
+ "\tnumber of executors {2}",
|
|
|
|
|
new Object[] { vmname, osType, template.getNoOfParallelJobs() });
|
|
|
|
|
new Object[]{vmname, osType, template.getNoOfParallelJobs()});
|
|
|
|
|
|
|
|
|
|
AzureVMCloud azureCloud = template.getAzureCloud();
|
|
|
|
|
|
|
|
|
@ -523,8 +526,10 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Gets a map of available locations mapping display name -> name (usable in template)
|
|
|
|
|
* @return
|
|
|
|
|
* Gets a map of available locations mapping display name -> name (usable in
|
|
|
|
|
* template)
|
|
|
|
|
*
|
|
|
|
|
* @return
|
|
|
|
|
*/
|
|
|
|
|
private static Map<String, String> getAvailableLocationsStandard() {
|
|
|
|
|
final Map<String, String> locations = new HashMap<String, String>();
|
|
|
|
@ -547,55 +552,56 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
locations.put("West India", "westindia");
|
|
|
|
|
return locations;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private static Map<String, String> getAvailableLocationsChina() {
|
|
|
|
|
final Map<String, String> locations = new HashMap<String, String>();
|
|
|
|
|
locations.put("China North", "chinanorth");
|
|
|
|
|
locations.put("China East", "chinaeast");
|
|
|
|
|
return locations;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private static Map<String, String> getAvailableLocationsAll() {
|
|
|
|
|
final Map<String, String> locations = new HashMap<String, String>();
|
|
|
|
|
locations.putAll(getAvailableLocationsStandard());
|
|
|
|
|
locations.putAll(getAvailableLocationsChina());
|
|
|
|
|
return locations;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Creates a map containing location -> vm role size list.
|
|
|
|
|
* This is hard coded and should be removed eventually once a transition to
|
|
|
|
|
* the 1.0.0 SDK is made
|
|
|
|
|
* @return New map
|
|
|
|
|
* Creates a map containing location -> vm role size list. This is hard
|
|
|
|
|
* coded and should be removed eventually once a transition to the 1.0.0 SDK
|
|
|
|
|
* is made
|
|
|
|
|
*
|
|
|
|
|
* @return New map
|
|
|
|
|
*/
|
|
|
|
|
private static Map<String, List<String>> getAvailableRoleSizes() {
|
|
|
|
|
final Map<String, List<String>> sizes = new HashMap<String, List<String>>();
|
|
|
|
|
sizes.put("East US", Arrays.asList(new String[] {"A10","A11","A5","A6","A7","A8","A9","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("West US", Arrays.asList(new String[] {"A10","A11","A5","A6","A7","A8","A9","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s","Standard_G1","Standard_G2","Standard_G3","Standard_G4","Standard_G5","Standard_GS1","Standard_GS2","Standard_GS3","Standard_GS4","Standard_GS5"}));
|
|
|
|
|
sizes.put("South Central US", Arrays.asList(new String[] {"A10","A11","A5","A6","A7","A8","A9","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("Central US", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("North Central US", Arrays.asList(new String[] {"A10","A11","A5","A6","A7","A8","A9","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1_v2","Standard_DS11_v2","Standard_DS12_v2","Standard_DS13_v2","Standard_DS14_v2","Standard_DS2_v2","Standard_DS3_v2","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("East US 2", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s","Standard_G1","Standard_G2","Standard_G3","Standard_G4","Standard_G5","Standard_GS1","Standard_GS2","Standard_GS3","Standard_GS4","Standard_GS5"}));
|
|
|
|
|
sizes.put("North Europe", Arrays.asList(new String[] {"A10","A11","A5","A6","A7","A8","A9","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("West Europe", Arrays.asList(new String[] {"A10","A11","A5","A6","A7","A8","A9","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s","Standard_G1","Standard_G2","Standard_G3","Standard_G4","Standard_G5","Standard_GS1","Standard_GS2","Standard_GS3","Standard_GS4","Standard_GS5"}));
|
|
|
|
|
sizes.put("Southeast Asia", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s","Standard_G1","Standard_G2","Standard_G3","Standard_G4","Standard_G5","Standard_GS1","Standard_GS2","Standard_GS3","Standard_GS4","Standard_GS5"}));
|
|
|
|
|
sizes.put("East Asia", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS11","Standard_DS12","Standard_DS13","Standard_DS14","Standard_DS2","Standard_DS3","Standard_DS4","Standard_F1","Standard_F16","Standard_F2","Standard_F4","Standard_F8"}));
|
|
|
|
|
sizes.put("Japan West", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("Japan East", Arrays.asList(new String[] {"A10","A11","A5","A6","A7","A8","A9","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("Brazil South", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1_v2","Standard_DS11_v2","Standard_DS12_v2","Standard_DS13_v2","Standard_DS14_v2","Standard_DS2_v2","Standard_DS3_v2","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("Australia Southeast", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("Australia East", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s","Standard_G1","Standard_G2","Standard_G3","Standard_G4","Standard_G5","Standard_GS1","Standard_GS2","Standard_GS3","Standard_GS4","Standard_GS5"}));
|
|
|
|
|
sizes.put("Central India", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1_v2","Standard_D11_v2","Standard_D12_v2","Standard_D13_v2","Standard_D14_v2","Standard_D2_v2","Standard_D3_v2","Standard_D4_v2","Standard_D5_v2","Standard_DS1_v2","Standard_DS11_v2","Standard_DS12_v2","Standard_DS13_v2","Standard_DS14_v2","Standard_DS2_v2","Standard_DS3_v2","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("South India", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1_v2","Standard_D11_v2","Standard_D12_v2","Standard_D13_v2","Standard_D14_v2","Standard_D2_v2","Standard_D3_v2","Standard_D4_v2","Standard_D5_v2","Standard_DS1_v2","Standard_DS11_v2","Standard_DS12_v2","Standard_DS13_v2","Standard_DS14_v2","Standard_DS2_v2","Standard_DS3_v2","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s"}));
|
|
|
|
|
sizes.put("West India", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1_v2","Standard_D11_v2","Standard_D12_v2","Standard_D13_v2","Standard_D14_v2","Standard_D2_v2","Standard_D3_v2","Standard_D4_v2","Standard_D5_v2","Standard_F1","Standard_F16","Standard_F2","Standard_F4","Standard_F8"}));
|
|
|
|
|
sizes.put("East US", Arrays.asList(new String[]{"A10", "A11", "A5", "A6", "A7", "A8", "A9", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("West US", Arrays.asList(new String[]{"A10", "A11", "A5", "A6", "A7", "A8", "A9", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s", "Standard_G1", "Standard_G2", "Standard_G3", "Standard_G4", "Standard_G5", "Standard_GS1", "Standard_GS2", "Standard_GS3", "Standard_GS4", "Standard_GS5"}));
|
|
|
|
|
sizes.put("South Central US", Arrays.asList(new String[]{"A10", "A11", "A5", "A6", "A7", "A8", "A9", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("Central US", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("North Central US", Arrays.asList(new String[]{"A10", "A11", "A5", "A6", "A7", "A8", "A9", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1_v2", "Standard_DS11_v2", "Standard_DS12_v2", "Standard_DS13_v2", "Standard_DS14_v2", "Standard_DS2_v2", "Standard_DS3_v2", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("East US 2", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s", "Standard_G1", "Standard_G2", "Standard_G3", "Standard_G4", "Standard_G5", "Standard_GS1", "Standard_GS2", "Standard_GS3", "Standard_GS4", "Standard_GS5"}));
|
|
|
|
|
sizes.put("North Europe", Arrays.asList(new String[]{"A10", "A11", "A5", "A6", "A7", "A8", "A9", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("West Europe", Arrays.asList(new String[]{"A10", "A11", "A5", "A6", "A7", "A8", "A9", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s", "Standard_G1", "Standard_G2", "Standard_G3", "Standard_G4", "Standard_G5", "Standard_GS1", "Standard_GS2", "Standard_GS3", "Standard_GS4", "Standard_GS5"}));
|
|
|
|
|
sizes.put("Southeast Asia", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s", "Standard_G1", "Standard_G2", "Standard_G3", "Standard_G4", "Standard_G5", "Standard_GS1", "Standard_GS2", "Standard_GS3", "Standard_GS4", "Standard_GS5"}));
|
|
|
|
|
sizes.put("East Asia", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS11", "Standard_DS12", "Standard_DS13", "Standard_DS14", "Standard_DS2", "Standard_DS3", "Standard_DS4", "Standard_F1", "Standard_F16", "Standard_F2", "Standard_F4", "Standard_F8"}));
|
|
|
|
|
sizes.put("Japan West", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("Japan East", Arrays.asList(new String[]{"A10", "A11", "A5", "A6", "A7", "A8", "A9", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("Brazil South", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1_v2", "Standard_DS11_v2", "Standard_DS12_v2", "Standard_DS13_v2", "Standard_DS14_v2", "Standard_DS2_v2", "Standard_DS3_v2", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("Australia Southeast", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("Australia East", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s", "Standard_G1", "Standard_G2", "Standard_G3", "Standard_G4", "Standard_G5", "Standard_GS1", "Standard_GS2", "Standard_GS3", "Standard_GS4", "Standard_GS5"}));
|
|
|
|
|
sizes.put("Central India", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1_v2", "Standard_D11_v2", "Standard_D12_v2", "Standard_D13_v2", "Standard_D14_v2", "Standard_D2_v2", "Standard_D3_v2", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1_v2", "Standard_DS11_v2", "Standard_DS12_v2", "Standard_DS13_v2", "Standard_DS14_v2", "Standard_DS2_v2", "Standard_DS3_v2", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("South India", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1_v2", "Standard_D11_v2", "Standard_D12_v2", "Standard_D13_v2", "Standard_D14_v2", "Standard_D2_v2", "Standard_D3_v2", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1_v2", "Standard_DS11_v2", "Standard_DS12_v2", "Standard_DS13_v2", "Standard_DS14_v2", "Standard_DS2_v2", "Standard_DS3_v2", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s"}));
|
|
|
|
|
sizes.put("West India", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1_v2", "Standard_D11_v2", "Standard_D12_v2", "Standard_D13_v2", "Standard_D14_v2", "Standard_D2_v2", "Standard_D3_v2", "Standard_D4_v2", "Standard_D5_v2", "Standard_F1", "Standard_F16", "Standard_F2", "Standard_F4", "Standard_F8"}));
|
|
|
|
|
|
|
|
|
|
// China sizes, may not be exact
|
|
|
|
|
sizes.put("China North", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS1_v2","Standard_DS11","Standard_DS11_v2","Standard_DS12","Standard_DS12_v2","Standard_DS13","Standard_DS13_v2","Standard_DS14","Standard_DS14_v2","Standard_DS2","Standard_DS2_v2","Standard_DS3","Standard_DS3_v2","Standard_DS4","Standard_DS4_v2","Standard_DS5_v2","Standard_F1","Standard_F16","Standard_F16s","Standard_F1s","Standard_F2","Standard_F2s","Standard_F4","Standard_F4s","Standard_F8","Standard_F8s","Standard_G1","Standard_G2","Standard_G3","Standard_G4","Standard_G5","Standard_GS1","Standard_GS2","Standard_GS3","Standard_GS4","Standard_GS5"}));
|
|
|
|
|
sizes.put("China East", Arrays.asList(new String[] {"A5","A6","A7","Basic_A0","Basic_A1","Basic_A2","Basic_A3","Basic_A4","ExtraLarge","ExtraSmall","Large","Medium","Small","Standard_D1","Standard_D1_v2","Standard_D11","Standard_D11_v2","Standard_D12","Standard_D12_v2","Standard_D13","Standard_D13_v2","Standard_D14","Standard_D14_v2","Standard_D2","Standard_D2_v2","Standard_D3","Standard_D3_v2","Standard_D4","Standard_D4_v2","Standard_D5_v2","Standard_DS1","Standard_DS11","Standard_DS12","Standard_DS13","Standard_DS14","Standard_DS2","Standard_DS3","Standard_DS4","Standard_F1","Standard_F16","Standard_F2","Standard_F4","Standard_F8"}));
|
|
|
|
|
|
|
|
|
|
sizes.put("China North", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS1_v2", "Standard_DS11", "Standard_DS11_v2", "Standard_DS12", "Standard_DS12_v2", "Standard_DS13", "Standard_DS13_v2", "Standard_DS14", "Standard_DS14_v2", "Standard_DS2", "Standard_DS2_v2", "Standard_DS3", "Standard_DS3_v2", "Standard_DS4", "Standard_DS4_v2", "Standard_DS5_v2", "Standard_F1", "Standard_F16", "Standard_F16s", "Standard_F1s", "Standard_F2", "Standard_F2s", "Standard_F4", "Standard_F4s", "Standard_F8", "Standard_F8s", "Standard_G1", "Standard_G2", "Standard_G3", "Standard_G4", "Standard_G5", "Standard_GS1", "Standard_GS2", "Standard_GS3", "Standard_GS4", "Standard_GS5"}));
|
|
|
|
|
sizes.put("China East", Arrays.asList(new String[]{"A5", "A6", "A7", "Basic_A0", "Basic_A1", "Basic_A2", "Basic_A3", "Basic_A4", "ExtraLarge", "ExtraSmall", "Large", "Medium", "Small", "Standard_D1", "Standard_D1_v2", "Standard_D11", "Standard_D11_v2", "Standard_D12", "Standard_D12_v2", "Standard_D13", "Standard_D13_v2", "Standard_D14", "Standard_D14_v2", "Standard_D2", "Standard_D2_v2", "Standard_D3", "Standard_D3_v2", "Standard_D4", "Standard_D4_v2", "Standard_D5_v2", "Standard_DS1", "Standard_DS11", "Standard_DS12", "Standard_DS13", "Standard_DS14", "Standard_DS2", "Standard_DS3", "Standard_DS4", "Standard_F1", "Standard_F16", "Standard_F2", "Standard_F4", "Standard_F8"}));
|
|
|
|
|
|
|
|
|
|
return sizes;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Gets map of Azure datacenter locations which supports Persistent VM role.
|
|
|
|
|
* Today this is hardcoded pulling from the array, because the old form of
|
|
|
|
@ -607,11 +613,11 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
}
|
|
|
|
|
return AVAILABLE_LOCATIONS_STD;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Gets list of virtual machine sizes.
|
|
|
|
|
* Currently hardcoded because the old vm size API does not support
|
|
|
|
|
* the new method of authentication
|
|
|
|
|
* Gets list of virtual machine sizes. Currently hardcoded because the old
|
|
|
|
|
* vm size API does not support the new method of authentication
|
|
|
|
|
*
|
|
|
|
|
* @param location Location to obtain VM sizes for
|
|
|
|
|
*/
|
|
|
|
|
public static List<String> getVMSizes(final String location) {
|
|
|
|
@ -623,38 +629,47 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
*
|
|
|
|
|
* @param servicePrincipal
|
|
|
|
|
* @param resourceGroupName
|
|
|
|
|
* @param maxVMLimit
|
|
|
|
|
* @param timeout
|
|
|
|
|
* @return
|
|
|
|
|
*/
|
|
|
|
|
public static String verifyConfiguration(
|
|
|
|
|
final AzureCredentials.ServicePrincipal servicePrincipal,
|
|
|
|
|
final String resourceGroupName) {
|
|
|
|
|
if (servicePrincipal.isBlank() || StringUtils.isBlank(resourceGroupName)) {
|
|
|
|
|
return Messages.Azure_GC_Template_Val_Profile_Missing();
|
|
|
|
|
} else {
|
|
|
|
|
try {
|
|
|
|
|
// Load up the configuration now and do a live verification
|
|
|
|
|
Configuration config = ServiceDelegateHelper.loadConfiguration(servicePrincipal);
|
|
|
|
|
|
|
|
|
|
if (!verifyConfiguration(config, resourceGroupName).equals(Constants.OP_SUCCESS)) {
|
|
|
|
|
final String resourceGroupName, final String maxVMLimit, final String timeOut) {
|
|
|
|
|
try {
|
|
|
|
|
Configuration config = ServiceDelegateHelper.loadConfiguration(servicePrincipal);
|
|
|
|
|
|
|
|
|
|
if(!AzureUtil.isValidTimeOut(timeOut))
|
|
|
|
|
return "Invalid Timeout, Should be a positive number, minimum value "+Constants.DEFAULT_DEPLOYMENT_TIMEOUT_SEC;
|
|
|
|
|
|
|
|
|
|
if(!AzureUtil.isValidResourceGroupName(resourceGroupName))
|
|
|
|
|
return "Error: "+Messages.Azure_GC_Template_ResourceGroupName_Err();
|
|
|
|
|
|
|
|
|
|
if(!AzureUtil.isValidMAxVMLimit(maxVMLimit))
|
|
|
|
|
return "Invalid Limit, Should be a positive number, e.g. "+Constants.DEFAULT_MAX_VM_LIMIT;
|
|
|
|
|
|
|
|
|
|
if (AzureUtil.isValidTimeOut(timeOut) && AzureUtil.isValidMAxVMLimit(maxVMLimit)
|
|
|
|
|
&& AzureUtil.isValidResourceGroupName(resourceGroupName)) {
|
|
|
|
|
|
|
|
|
|
String result = verifyConfiguration(config, resourceGroupName);
|
|
|
|
|
if (!result.matches(Constants.OP_SUCCESS))
|
|
|
|
|
return Messages.Azure_GC_Template_Val_Profile_Err();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.SEVERE, "Error validating profile", e);
|
|
|
|
|
return Messages.Azure_GC_Template_Val_Profile_Err();
|
|
|
|
|
}
|
|
|
|
|
}catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.SEVERE, "Error validating profile", e);
|
|
|
|
|
return Messages.Azure_GC_Template_Val_Profile_Err();
|
|
|
|
|
}
|
|
|
|
|
return Constants.OP_SUCCESS;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public static String verifyConfiguration(final Configuration config, final String resourceGroupName) {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Callable<String> task = new Callable<String>() {
|
|
|
|
|
|
|
|
|
|
@Override
|
|
|
|
|
public String call() throws Exception {
|
|
|
|
|
ServiceDelegateHelper.getStorageManagementClient(config).getStorageAccountsOperations().
|
|
|
|
|
checkNameAvailability("CI_SYSTEM");
|
|
|
|
|
checkNameAvailability("CI_SYSTEM");
|
|
|
|
|
return Constants.OP_SUCCESS;
|
|
|
|
|
}
|
|
|
|
|
};
|
|
|
|
@ -697,14 +712,15 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: getVirtualMachineStatus:\n\tPowerState: {0}\n\tProvisioning: {1}",
|
|
|
|
|
new Object[] { powerstatus, provisioning });
|
|
|
|
|
new Object[]{powerstatus, provisioning});
|
|
|
|
|
|
|
|
|
|
return "succeeded".equalsIgnoreCase(provisioning)
|
|
|
|
|
? powerstatus.toUpperCase() : Constants.PROVISIONING_OR_DEPROVISIONING_VM_STATUS;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Checks if VM is reachable and in a valid state to connect (or getting ready to do so).
|
|
|
|
|
* Checks if VM is reachable and in a valid state to connect (or getting
|
|
|
|
|
* ready to do so).
|
|
|
|
|
*
|
|
|
|
|
* @param agent
|
|
|
|
|
* @return
|
|
|
|
@ -715,16 +731,16 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
String status = getVirtualMachineStatus(config, agent.getNodeName(), agent.getResourceGroupName());
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: isVMAliveOrHealthy: status {0}", status);
|
|
|
|
|
return !(Constants.PROVISIONING_OR_DEPROVISIONING_VM_STATUS.equalsIgnoreCase(status)
|
|
|
|
|
|| Constants.STOPPING_VM_STATUS.equalsIgnoreCase(status)
|
|
|
|
|
|| Constants.STOPPED_VM_STATUS.equalsIgnoreCase(status)
|
|
|
|
|
|| Constants.DEALLOCATED_VM_STATUS.equalsIgnoreCase(status));
|
|
|
|
|
|| Constants.STOPPING_VM_STATUS.equalsIgnoreCase(status)
|
|
|
|
|
|| Constants.STOPPED_VM_STATUS.equalsIgnoreCase(status)
|
|
|
|
|
|| Constants.DEALLOCATED_VM_STATUS.equalsIgnoreCase(status));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Retrieves count of virtual machine in a azure subscription. This count
|
|
|
|
|
* is based off of the VMs that the current credential set has access to. It also
|
|
|
|
|
* does not deal with the classic, model. So keep this in mind.
|
|
|
|
|
*
|
|
|
|
|
* Retrieves count of virtual machine in a azure subscription. This count is
|
|
|
|
|
* based off of the VMs that the current credential set has access to. It
|
|
|
|
|
* also does not deal with the classic, model. So keep this in mind.
|
|
|
|
|
*
|
|
|
|
|
* @param config Subscription configuration
|
|
|
|
|
* @return Total VM count
|
|
|
|
|
* @throws Exception
|
|
|
|
@ -758,15 +774,14 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
*/
|
|
|
|
|
public static void shutdownVirtualMachine(final AzureVMAgent agent) {
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: shutdownVirtualMachine: called for {0}",
|
|
|
|
|
agent.getNodeName() );
|
|
|
|
|
|
|
|
|
|
agent.getNodeName());
|
|
|
|
|
|
|
|
|
|
try {
|
|
|
|
|
ServiceDelegateHelper.getComputeManagementClient(agent).
|
|
|
|
|
getVirtualMachinesOperations().powerOff(agent.getResourceGroupName(), agent.getNodeName());
|
|
|
|
|
}
|
|
|
|
|
catch (Exception e) {
|
|
|
|
|
getVirtualMachinesOperations().powerOff(agent.getResourceGroupName(), agent.getNodeName());
|
|
|
|
|
} catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: provision: could not terminate or shutdown {0}, {1}",
|
|
|
|
|
new Object[] {agent.getNodeName(), e});
|
|
|
|
|
new Object[]{agent.getNodeName(), e});
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -784,12 +799,13 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Terminates a virtual machine
|
|
|
|
|
*
|
|
|
|
|
* @param config Azure configuration
|
|
|
|
|
* @param vmName VM name
|
|
|
|
|
* @param resourceGroupName Resource group containing the VM
|
|
|
|
|
* @throws Exception
|
|
|
|
|
* @throws Exception
|
|
|
|
|
*/
|
|
|
|
|
public static void terminateVirtualMachine(final Configuration config, final String vmName,
|
|
|
|
|
public static void terminateVirtualMachine(final Configuration config, final String vmName,
|
|
|
|
|
final String resourceGroupName) throws Exception {
|
|
|
|
|
try {
|
|
|
|
|
try {
|
|
|
|
@ -797,34 +813,34 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
final ComputeManagementClient client = ServiceDelegateHelper.getComputeManagementClient(config);
|
|
|
|
|
|
|
|
|
|
List<URI> diskUrisToRemove = new ArrayList<URI>();
|
|
|
|
|
StorageProfile storageProfile =
|
|
|
|
|
client.getVirtualMachinesOperations().get(resourceGroupName, vmName).getVirtualMachine().getStorageProfile();
|
|
|
|
|
StorageProfile storageProfile
|
|
|
|
|
= client.getVirtualMachinesOperations().get(resourceGroupName, vmName).getVirtualMachine().getStorageProfile();
|
|
|
|
|
// Remove the OS disks
|
|
|
|
|
diskUrisToRemove.add(new URI(storageProfile.getOSDisk().getVirtualHardDisk().getUri()));
|
|
|
|
|
// TODO: Remove data disks or add option to do so?
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Remove the VM
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: terminateVirtualMachine: Removing virtual machine {0}", vmName);
|
|
|
|
|
client.getVirtualMachinesOperations().delete(resourceGroupName, vmName);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Now remove the disks
|
|
|
|
|
for (URI diskUri : diskUrisToRemove) {
|
|
|
|
|
// Obtain container, storage account, and blob name
|
|
|
|
|
String storageAccountName = diskUri.getHost().split("\\.")[0];
|
|
|
|
|
String containerName = PathUtility.getContainerNameFromUri(diskUri, false);
|
|
|
|
|
String blobName = PathUtility.getBlobNameFromURI(diskUri, false);
|
|
|
|
|
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: terminateVirtualMachine: Removing disk blob {0}, in container {1} of storage account {2}",
|
|
|
|
|
new Object [] { blobName, containerName, storageAccountName } );
|
|
|
|
|
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: terminateVirtualMachine: Removing disk blob {0}, in container {1} of storage account {2}",
|
|
|
|
|
new Object[]{blobName, containerName, storageAccountName});
|
|
|
|
|
final StorageManagementClient storageClient = ServiceDelegateHelper.getStorageManagementClient(config);
|
|
|
|
|
StorageAccountKeys storageKeys =
|
|
|
|
|
storageClient.getStorageAccountsOperations().listKeys(resourceGroupName, storageAccountName).getStorageAccountKeys();
|
|
|
|
|
StorageAccountKeys storageKeys
|
|
|
|
|
= storageClient.getStorageAccountsOperations().listKeys(resourceGroupName, storageAccountName).getStorageAccountKeys();
|
|
|
|
|
URI blobURI = storageClient.getStorageAccountsOperations().getProperties(resourceGroupName, storageAccountName).getStorageAccount().getPrimaryEndpoints().getBlob();
|
|
|
|
|
CloudBlobContainer container = StorageServiceDelegate.getBlobContainerReference(
|
|
|
|
|
storageAccountName, storageKeys.getKey1(), blobURI.toString(), containerName);
|
|
|
|
|
storageAccountName, storageKeys.getKey1(), blobURI.toString(), containerName);
|
|
|
|
|
container.getBlockBlobReference(blobName).deleteIfExists();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Also remove the init script (if it exists)
|
|
|
|
|
}
|
|
|
|
|
} catch (ExecutionException ee) {
|
|
|
|
@ -863,16 +879,17 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Remove the IP name
|
|
|
|
|
* Remove the IP name
|
|
|
|
|
*
|
|
|
|
|
* @param config
|
|
|
|
|
* @param resourceGroupName
|
|
|
|
|
* @param vmName
|
|
|
|
|
* @throws AzureCloudException
|
|
|
|
|
* We probably should record and pass in NIC/IP names.
|
|
|
|
|
* Also, if we go away from 1 public IP address per system, then we will need to update this.
|
|
|
|
|
*
|
|
|
|
|
* @throws AzureCloudException We probably should record and pass in NIC/IP
|
|
|
|
|
* names. Also, if we go away from 1 public IP address per system, then we
|
|
|
|
|
* will need to update this.
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
|
private static void removeIPName(final Configuration config,
|
|
|
|
|
private static void removeIPName(final Configuration config,
|
|
|
|
|
final String resourceGroupName, final String vmName) throws AzureCloudException {
|
|
|
|
|
final NetworkResourceProviderClient client = ServiceDelegateHelper.getNetworkManagementClient(config);
|
|
|
|
|
|
|
|
|
@ -937,7 +954,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
} catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.INFO, "AzureVMManagementServiceDelegate: startVirtualMachine: got exception while "
|
|
|
|
|
+ "starting VM {0}. Will retry again after 30 seconds. Current retry count {1} / {2}\n",
|
|
|
|
|
new Object[] { agent.getNodeName(), retryCount, Constants.MAX_PROV_RETRIES });
|
|
|
|
|
new Object[]{agent.getNodeName(), retryCount, Constants.MAX_PROV_RETRIES});
|
|
|
|
|
if (retryCount > Constants.MAX_PROV_RETRIES) {
|
|
|
|
|
throw e;
|
|
|
|
|
} else {
|
|
|
|
@ -976,17 +993,18 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
}
|
|
|
|
|
return null;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Gets a final location name from a display name location.
|
|
|
|
|
*
|
|
|
|
|
* @param location
|
|
|
|
|
* @return
|
|
|
|
|
* @return
|
|
|
|
|
*/
|
|
|
|
|
private static String getLocationName(String location) {
|
|
|
|
|
if (AVAILABLE_LOCATIONS_ALL.containsKey(location)) {
|
|
|
|
|
return AVAILABLE_LOCATIONS_ALL.get(location);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return null;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -1043,21 +1061,20 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
|
|
|
|
|
List<String> errors = new ArrayList<String>();
|
|
|
|
|
Configuration config = null;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Load configuration
|
|
|
|
|
try {
|
|
|
|
|
config = ServiceDelegateHelper.loadConfiguration(servicePrincipal);
|
|
|
|
|
String validationResult;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Verify basic info about the template
|
|
|
|
|
|
|
|
|
|
//Verify number of parallel jobs
|
|
|
|
|
validationResult = verifyNoOfExecutors(noOfParallelJobs);
|
|
|
|
|
addValidationResultIfFailed(validationResult, errors);
|
|
|
|
|
if (returnOnSingleError && errors.size() > 0) {
|
|
|
|
|
return errors;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
validationResult = verifyRetentionTime(retentionTimeInMin);
|
|
|
|
|
addValidationResultIfFailed(validationResult, errors);
|
|
|
|
|
if (returnOnSingleError && errors.size() > 0) {
|
|
|
|
@ -1065,14 +1082,14 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//verify password
|
|
|
|
|
String adminPassword="";
|
|
|
|
|
String adminPassword = "";
|
|
|
|
|
try {
|
|
|
|
|
StandardUsernamePasswordCredentials creds = AzureUtil.getCredentials(credentialsId);
|
|
|
|
|
adminPassword = creds.getPassword().getPlainText();
|
|
|
|
|
} catch(AzureCloudException e) {
|
|
|
|
|
} catch (AzureCloudException e) {
|
|
|
|
|
LOGGER.log(Level.SEVERE, "Could not load the VM credentials", e);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
validationResult = verifyAdminPassword(adminPassword);
|
|
|
|
|
addValidationResultIfFailed(validationResult, errors);
|
|
|
|
|
if (returnOnSingleError && errors.size() > 0) {
|
|
|
|
@ -1091,7 +1108,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
if (returnOnSingleError && errors.size() > 0) {
|
|
|
|
|
return errors;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
validationResult = verifyLocation(location, servicePrincipal.serviceManagementURL);
|
|
|
|
|
addValidationResultIfFailed(validationResult, errors);
|
|
|
|
|
if (returnOnSingleError && errors.size() > 0) {
|
|
|
|
@ -1170,6 +1187,8 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
errors.add("Exception occured while validating temaplate " + executionException);
|
|
|
|
|
} catch (TimeoutException timeoutException) {
|
|
|
|
|
errors.add("Exception occured while validating temaplate " + timeoutException);
|
|
|
|
|
} catch (Exception others) {
|
|
|
|
|
errors.add(others.getMessage() + others);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
} catch (InterruptedException interruptedException) {
|
|
|
|
@ -1258,7 +1277,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
// storage account is the same as the target storage account.
|
|
|
|
|
// The URI for he storage account should be https://<storageaccountname>.
|
|
|
|
|
// Parse that out and verify agaisnt the image storageAccountName
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Check that the image string is a URI by attempting to create
|
|
|
|
|
// a URI
|
|
|
|
|
final URI u;
|
|
|
|
@ -1279,8 +1298,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
return Messages.Azure_GC_Template_ImageURI_Not_Valid();
|
|
|
|
|
}
|
|
|
|
|
return Constants.OP_SUCCESS;
|
|
|
|
|
}
|
|
|
|
|
catch (Exception e) {
|
|
|
|
|
} catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.SEVERE, "Invalid virtual machine image", e);
|
|
|
|
|
return Messages.Azure_GC_Template_ImageURI_Not_Valid();
|
|
|
|
|
}
|
|
|
|
@ -1300,14 +1318,12 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
// to the empty string
|
|
|
|
|
if (imageVersion.equalsIgnoreCase("latest")) {
|
|
|
|
|
params.setVersion("");
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
} else {
|
|
|
|
|
params.setVersion(imageVersion);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
client.get(params);
|
|
|
|
|
}
|
|
|
|
|
catch (Exception e) {
|
|
|
|
|
} catch (Exception e) {
|
|
|
|
|
LOGGER.log(Level.SEVERE, "Invalid virtual machine image", e);
|
|
|
|
|
return Messages.Azure_GC_Template_ImageReference_Not_Valid(e.getMessage());
|
|
|
|
|
}
|
|
|
|
@ -1334,11 +1350,12 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
return Messages.Azure_GC_JVM_Option_Err();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Check the location. This location is the display name.
|
|
|
|
|
* @param location
|
|
|
|
|
* @return
|
|
|
|
|
*
|
|
|
|
|
* @param location
|
|
|
|
|
* @return
|
|
|
|
|
*/
|
|
|
|
|
private static String verifyLocation(final String location, final String serviceManagementURL) {
|
|
|
|
|
String locationName = getLocationName(location);
|
|
|
|
@ -1350,14 +1367,16 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Verify the validity of the image parameters (does not verify actual values)
|
|
|
|
|
* Verify the validity of the image parameters (does not verify actual
|
|
|
|
|
* values)
|
|
|
|
|
*
|
|
|
|
|
* @param image
|
|
|
|
|
* @param osType
|
|
|
|
|
* @param imagePublisher
|
|
|
|
|
* @param imageOffer
|
|
|
|
|
* @param imageSku
|
|
|
|
|
* @param imageVersion
|
|
|
|
|
* @return
|
|
|
|
|
* @return
|
|
|
|
|
*/
|
|
|
|
|
private static String verifyImageParameters(
|
|
|
|
|
final String image,
|
|
|
|
@ -1376,8 +1395,7 @@ public class AzureVMManagementServiceDelegate {
|
|
|
|
|
Messages.Azure_GC_Template_ImageURI_Not_Valid();
|
|
|
|
|
}
|
|
|
|
|
return Constants.OP_SUCCESS;
|
|
|
|
|
}
|
|
|
|
|
else if (StringUtils.isNotBlank(imagePublisher)
|
|
|
|
|
} else if (StringUtils.isNotBlank(imagePublisher)
|
|
|
|
|
&& StringUtils.isNotBlank(imageOffer)
|
|
|
|
|
&& StringUtils.isNotBlank(imageSku)
|
|
|
|
|
&& StringUtils.isNotBlank(imageVersion)) {
|
|
|
|
|