-
+
+
@@ -114,7 +125,6 @@
-
+ with="subscriptionId,clientId,clientSecret,oauth2TokenEndpoint,serviceManagementURL,resourceGroupName,templateName,labels,location,virtualMachineSize,storageAccountName,noOfParallelJobs,image,osType,imagePublisher,imageOffer,imageSku,imageVersion,slaveLaunchMethod,initScript,adminUserName,adminPassword,virtualNetworkName,subnetName,retentionTimeInMin,jvmOptions" />
diff --git a/src/main/resources/com/microsoftopentechnologies/azure/AzureSlaveTemplate/config.properties b/src/main/resources/com/microsoftopentechnologies/azure/AzureSlaveTemplate/config.properties
index 0b94df3..0e3f362 100644
--- a/src/main/resources/com/microsoftopentechnologies/azure/AzureSlaveTemplate/config.properties
+++ b/src/main/resources/com/microsoftopentechnologies/azure/AzureSlaveTemplate/config.properties
@@ -22,7 +22,10 @@ Image_Version=Image Version
Launch_Method=Launch Method
-Init_Script=Init Script
+Initialization_Configuration=VM First Startup Configuration
+Init_Script=Initialization Script
+Execute_Init_Script_As_Root=Run Initialization Script As Root (Linux Only)
+Do_Not_Use_Machine_If_Init_Fails=Don't Use VM If Initialization Script Fails (Linux Only)
Username=Username
Password=Password
@@ -32,7 +35,7 @@ JVM_Options=JVM Options
#CloudServiceName=Cloud Service Name
RetentionTimeInMin=Retention Time (in minutes)
-Template_Status=Slave Provisioning
+Template_Is_Disabled=Disable template.
Template_Status_Details=Provisioning Failure Reason
Delete_Template=Delete Template
Verify_Template=Verify Template
diff --git a/src/main/resources/com/microsoftopentechnologies/azure/Messages.properties b/src/main/resources/com/microsoftopentechnologies/azure/Messages.properties
index 97dd78d..69d5fa0 100644
--- a/src/main/resources/com/microsoftopentechnologies/azure/Messages.properties
+++ b/src/main/resources/com/microsoftopentechnologies/azure/Messages.properties
@@ -1,10 +1,12 @@
# Global configuration - validations
Azure_Config_Success=Successfully verified Azure configuration.
Azure_GC_InitScript_Warn_Msg=Ensure image is pre-configured with a Java runtime or provide a script to install Java in headless (silent) mode. \
- \nIf using JNLP, refer here for a sample script.
+ \nIf using JNLP, see README.md for a sample script.
Azure_GC_LaunchMethod_Warn_Msg=Make sure the Azure slave can reach the master via the Jenkins URL. Refer to the help for details.
Azure_GC_TemplateStatus_Warn_Msg=The template is marked as disabled. Check the template status details in the Advanced section.
+Azure_GC_OS_Type_Unknown_Err=Unknown OS type. Should be Linux or Windows
+
Azure_GC_UserName_Err=Not a valid user name. The user name must contain between 3 and 15 characters: alphanumerics, the underscore or the hyphen.
Azure_GC_Password_Err=Required: Not a valid password. Refer to the password rules in the help.
Azure_GC_JVM_Option_Err=Error: Not a valid JVM Option. JVM options should start with a hyphen(-). e.g. -Xmx1500m
@@ -15,7 +17,9 @@ Azure_GC_Template_Val_Profile_Err=Failed to validate the Azure profile. Verify t
Azure_GC_Template_max_VM_Err=The current number of virtual machines in this Azure subscription is {0}, which is more than or equal to the default value {1} \
\n.Consider increasing Max Virtual Machines Limit value or delete existing virtual machines from your subscription.
Azure_GC_Template_Null_Or_Empty=The template name is null or empty.
-Azure_GC_Template_Name_NA=The cloud service name {0} is either not available or not valid. Use a different template name.
+Azure_GC_Template_Name_Not_Valid=The template name is not valid. Must begin with a letter, and contain only letters, numbers, or dashes
+Azure_GC_Template_Name_Shortened=The template name is valid, but VM names will be shortened to: {0}
+Azure_GC_Template_LOC_Not_Found=The location is not valid
Azure_GC_Template_Name_LOC_No_Match=The cloud service location and the location selected do not match. Use a different template or location.
Azure_GC_Template_CS_NA=Cloud service name {0} is either not available or not valid. Use a different cloud service name.
Azure_GC_Template_CS_LOC_No_Match=The cloud service location and the location selected do not match. Use a different cloud service or location.
@@ -26,8 +30,9 @@ Azure_GC_Template_Executors_Not_Positive=The number of executors must be a posit
Azure_GC_Template_RT_Null_Or_Empty=Missing retention time.
Azure_GC_Template_RT_Not_Positive=The retention time must be a positive integer.
Azure_GC_Template_ImageFamilyOrID_Null_Or_Empty=Missing image family or image ID.
-Azure_GC_Template_ImageFamilyOrID_Not_Valid=Failed to validate the provided image family or image ID. Make sure to reference a image that is available.
-Azure_GC_Template_ImageFamilyOrID_LOC_No_Match=The selected location is not among the locations where the image {0} is available.
+Azure_GC_Template_ImageURI_Not_Valid=Failed to validate the provided image location.
+Azure_GC_Template_ImageReference_Not_Valid=Failed to validate the provided image reference: {0}
+Azure_GC_Template_ImageURI_Not_In_Same_Account=The image URI is not located in the same storage account as the target storage account for the VM
Azure_GC_Template_JNLP_Not_Supported=The JNLP launch method is supported only for Windows.
Azure_GC_Template_UN_Null_Or_Empty=Missing admin user name.
Azure_GC_Template_PWD_Null_Or_Empty=Missing admin password.
@@ -38,15 +43,18 @@ Azure_GC_Template_subnet_NotFound=The subnet {0} does not belong to the specifie
Azure_Template_Config_Success=Verified the template configuration successfully.
-# Used internally in code and may appear in slave configuration or template status details
-Delete_Slave=Node is marked for deletion.
-IDLE_TIMEOUT_SHUTDOWN="Node is stopped(Deallocated) by Jenkins after Idle timeout"
+Failed_Initial_Shutdown_Or_Delete=Node failed initial shutdown/deletion. Marking as delete, will be cleaned up later.
+Idle_Timeout_Shutdown=Node is being stopped(Deallocated) by Jenkins after idle timeout
+Idle_Timeout_Delete=Node is being deleted by Jenkins after idle timeout
+User_Delete=Node is being deleted by the user
Slave_Failed_To_Connect=The slave failed to connect. The node has been marked for deletion. Make sure that the appropriate firewall exceptions have been configured \
for the slave to connect to the master.
+Slave_Failed_Init_Script=The slave connected, but failed its initialization script. The node has been marked for deletion.
+Shutdown_Slave_Failed_To_Revive=The previously shut down slave failed to start.
# Post build action for deprovisioning
-Azure_Slave_Post_Build_Action=Configure a post build action for the Azure slave.
-Build_Action_Shutdown_Slave=Shutdown Azure slave.
-Build_Action_Delete_Slave=Delete Azure slave after job execution.
-Build_Action_Delete_Slave_If_Not_Success=Delete Azure slave if the build is not successful.
+Azure_Slave_Post_Build_Action=Perform an action if the job was performed on an Azure Slave.
+Build_Action_Shutdown_Slave=Shutdown Azure slave after build execution.
+Build_Action_Delete_Slave=Delete slave after build execution (when idle).
+Build_Action_Delete_Slave_If_Not_Success=Delete slave if the build was not successful (when idle).
SA_Blank_Create_New=(Leave blank to create a new storage account)
diff --git a/src/main/resources/customImageTemplate.json b/src/main/resources/customImageTemplate.json
new file mode 100644
index 0000000..ad83e92
--- /dev/null
+++ b/src/main/resources/customImageTemplate.json
@@ -0,0 +1,135 @@
+{
+ "$schema": "http://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json",
+ "contentVersion": "1.0.0.0",
+ "parameters": {
+ },
+ "variables": {
+ "virtualNetworkName": "jenkinsarm-vnet",
+ "subnetName": "jenkinsarm-snet",
+ "storageAccountName": "jenkinsarmst",
+ "vnetID": "[resourceId('Microsoft.Network/virtualNetworks', variables('virtualNetworkName'))]",
+ "subnetRef": "[concat(variables('vnetID'),'/subnets/',variables('subnetName'))]",
+ "addressPrefix": "10.0.0.0/16",
+ "subnetPrefix": "10.0.0.0/24",
+ "publicIPAddressType": "Dynamic",
+ "storageAccountContainerName": "vhds",
+ "storageAccountType": "Standard_LRS"
+ },
+ "resources": [
+ {
+ "type": "Microsoft.Storage/storageAccounts",
+ "name": "[variables('storageAccountName')]",
+ "apiVersion": "2015-05-01-preview",
+ "location": "[variables('location')]",
+ "properties": {
+ "accountType": "[variables('storageAccountType')]"
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/virtualNetworks",
+ "name": "[variables('virtualNetworkName')]",
+ "location": "[variables('location')]",
+ "properties": {
+ "addressSpace": {
+ "addressPrefixes": [
+ "[variables('addressPrefix')]"
+ ]
+ },
+ "subnets": [{
+ "name": "[variables('subnetName')]",
+ "properties": {
+ "addressPrefix": "[variables('subnetPrefix')]"
+ }
+ }
+ ]
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/publicIPAddresses",
+ "name": "[concat(variables('vmName'), copyIndex(), 'IPName')]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "properties": {
+ "publicIPAllocationMethod": "[variables('publicIPAddressType')]",
+ "dnsSettings": {
+ "domainNameLabel": "[concat(variables('vmName'), copyIndex())]"
+ }
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/networkInterfaces",
+ "name": "[concat(variables('vmName'), copyIndex(), 'NIC')]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "dependsOn": [
+ "[concat('Microsoft.Network/publicIPAddresses/', variables('vmName'), copyIndex(), 'IPName')]",
+ "[concat('Microsoft.Network/virtualNetworks/', variables('virtualNetworkName'))]"
+ ],
+ "properties": {
+ "ipConfigurations": [{
+ "name": "ipconfig1",
+ "properties": {
+ "privateIPAllocationMethod": "Dynamic",
+ "publicIPAddress": {
+ "id": "[resourceId('Microsoft.Network/publicIPAddresses', concat(variables('vmName'), copyIndex(), 'IPName'))]"
+ },
+ "subnet": {
+ "id": "[variables('subnetRef')]"
+ }
+ }
+ }]
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Compute/virtualMachines",
+ "name": "[concat(variables('vmName'), copyIndex())]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "dependsOn": [
+ "[concat('Microsoft.Storage/storageAccounts/', variables('storageAccountName'))]",
+ "[concat('Microsoft.Network/networkInterfaces/', variables('vmName'), copyIndex(), 'NIC')]"
+ ],
+ "properties": {
+ "hardwareProfile": {
+ "vmSize": "[variables('vmSize')]"
+ },
+ "osProfile": {
+ "computername": "[concat(variables('vmName'), copyIndex())]",
+ "adminUsername": "[variables('adminUsername')]",
+ "adminPassword": "[variables('adminPassword')]"
+ },
+ "storageProfile": {
+ "osDisk": {
+ "name": "[concat(variables('vmName'), copyIndex())]",
+ "osType": "[variables('osType')]",
+ "caching": "ReadWrite",
+ "image": {
+ "uri": "[variables('image')]"
+ },
+ "createOption": "FromImage",
+ "vhd": {
+ "uri": "[concat('http://',variables('storageAccountName'),'.blob.core.windows.net/',variables('storageAccountContainerName'),'/', variables('vmName'), copyIndex(), 'OSDisk.vhd')]"
+ }
+ }
+ },
+ "networkProfile": {
+ "networkInterfaces": [{
+ "id": "[resourceId('Microsoft.Network/networkInterfaces', concat(variables('vmName'), copyIndex(), 'NIC'))]"
+ }]
+ }
+ }
+ }]
+}
\ No newline at end of file
diff --git a/src/main/resources/customImageTemplateWithScript.json b/src/main/resources/customImageTemplateWithScript.json
new file mode 100644
index 0000000..0797257
--- /dev/null
+++ b/src/main/resources/customImageTemplateWithScript.json
@@ -0,0 +1,170 @@
+{
+ "$schema": "http://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json",
+ "contentVersion": "1.0.0.0",
+ "parameters": {
+ "storageAccountKey" : {
+ "type" : "secureString"
+ }
+ },
+ "variables": {
+ "virtualNetworkName": "jenkinsarm-vnet",
+ "subnetName": "jenkinsarm-snet",
+ "storageAccountName": "jenkinsarmst",
+ "vnetID": "[resourceId('Microsoft.Network/virtualNetworks', variables('virtualNetworkName'))]",
+ "subnetRef": "[concat(variables('vnetID'),'/subnets/',variables('subnetName'))]",
+ "addressPrefix": "10.0.0.0/16",
+ "subnetPrefix": "10.0.0.0/24",
+ "publicIPAddressType": "Dynamic",
+ "storageAccountContainerName": "vhds",
+ "storageAccountType": "Standard_LRS",
+ "startupScriptURI": "",
+ "startupScriptName": "",
+ "jenkinsServerURL": "",
+ "clientSecrets": []
+ },
+ "resources": [
+ {
+ "type": "Microsoft.Storage/storageAccounts",
+ "name": "[variables('storageAccountName')]",
+ "apiVersion": "2015-05-01-preview",
+ "location": "[variables('location')]",
+ "properties": {
+ "accountType": "[variables('storageAccountType')]"
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/virtualNetworks",
+ "name": "[variables('virtualNetworkName')]",
+ "location": "[variables('location')]",
+ "properties": {
+ "addressSpace": {
+ "addressPrefixes": [
+ "[variables('addressPrefix')]"
+ ]
+ },
+ "subnets": [{
+ "name": "[variables('subnetName')]",
+ "properties": {
+ "addressPrefix": "[variables('subnetPrefix')]"
+ }
+ }
+ ]
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/publicIPAddresses",
+ "name": "[concat(variables('vmName'), copyIndex(), 'IPName')]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "properties": {
+ "publicIPAllocationMethod": "[variables('publicIPAddressType')]",
+ "dnsSettings": {
+ "domainNameLabel": "[concat(variables('vmName'), copyIndex())]"
+ }
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/networkInterfaces",
+ "name": "[concat(variables('vmName'), copyIndex(), 'NIC')]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "dependsOn": [
+ "[concat('Microsoft.Network/publicIPAddresses/', variables('vmName'), copyIndex(), 'IPName')]",
+ "[concat('Microsoft.Network/virtualNetworks/', variables('virtualNetworkName'))]"
+ ],
+ "properties": {
+ "ipConfigurations": [{
+ "name": "ipconfig1",
+ "properties": {
+ "privateIPAllocationMethod": "Dynamic",
+ "publicIPAddress": {
+ "id": "[resourceId('Microsoft.Network/publicIPAddresses', concat(variables('vmName'), copyIndex(), 'IPName'))]"
+ },
+ "subnet": {
+ "id": "[variables('subnetRef')]"
+ }
+ }
+ }]
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Compute/virtualMachines",
+ "name": "[concat(variables('vmName'), copyIndex())]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "dependsOn": [
+ "[concat('Microsoft.Storage/storageAccounts/', variables('storageAccountName'))]",
+ "[concat('Microsoft.Network/networkInterfaces/', variables('vmName'), copyIndex(), 'NIC')]"
+ ],
+ "properties": {
+ "hardwareProfile": {
+ "vmSize": "[variables('vmSize')]"
+ },
+ "osProfile": {
+ "computername": "[concat(variables('vmName'), copyIndex())]",
+ "adminUsername": "[variables('adminUsername')]",
+ "adminPassword": "[variables('adminPassword')]"
+ },
+ "storageProfile": {
+ "osDisk": {
+ "name": "[concat(variables('vmName'), copyIndex())]",
+ "osType": "[variables('osType')]",
+ "caching": "ReadWrite",
+ "image": {
+ "uri": "[variables('image')]"
+ },
+ "createOption": "FromImage",
+ "vhd": {
+ "uri": "[concat('http://',variables('storageAccountName'),'.blob.core.windows.net/',variables('storageAccountContainerName'),'/', variables('vmName'), copyIndex(), 'OSDisk.vhd')]"
+ }
+ }
+ },
+ "networkProfile": {
+ "networkInterfaces": [{
+ "id": "[resourceId('Microsoft.Network/networkInterfaces', concat(variables('vmName'), copyIndex(), 'NIC'))]"
+ }]
+ }
+ },
+ "resources" : [
+ {
+ "type": "extensions",
+ "name": "[concat('customScript', variables('vmName'), copyIndex())]",
+ "apiVersion": "2015-05-01-preview",
+ "location": "[variables('location')]",
+ "dependsOn": [
+ "[concat('Microsoft.Compute/virtualMachines/', variables('vmName'), copyIndex())]"
+ ],
+ "properties": {
+ "publisher": "Microsoft.Compute",
+ "type": "CustomScriptExtension",
+ "typeHandlerVersion": "1.7",
+ "autoUpgradeMinorVersion": true,
+ "settings": {
+ "fileUris": [
+ "[variables('startupScriptURI')]"
+ ],
+ "commandToExecute": "[concat('powershell.exe -ExecutionPolicy Unrestricted -File ', variables('startupScriptName'),' ', variables('jenkinsServerURL'),' ', variables('vmName'),copyIndex(),' ', variables('clientSecrets')[copyIndex()])]"
+ },
+ "protectedSettings": {
+ "storageAccountName" : "[variables('storageAccountName')]",
+ "storageAccountKey" : "[parameters('storageAccountKey')]"
+ }
+ }
+ }
+ ]
+ }
+ ]
+}
\ No newline at end of file
diff --git a/src/main/resources/referenceImageTemplate.json b/src/main/resources/referenceImageTemplate.json
new file mode 100644
index 0000000..461024a
--- /dev/null
+++ b/src/main/resources/referenceImageTemplate.json
@@ -0,0 +1,137 @@
+{
+ "$schema": "http://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json",
+ "contentVersion": "1.0.0.0",
+ "parameters": {
+ },
+ "variables": {
+ "virtualNetworkName": "jenkinsarm-vnet",
+ "subnetName": "jenkinsarm-snet",
+ "storageAccountName": "jenkinsarmst",
+ "vnetID": "[resourceId('Microsoft.Network/virtualNetworks', variables('virtualNetworkName'))]",
+ "subnetRef": "[concat(variables('vnetID'),'/subnets/',variables('subnetName'))]",
+ "addressPrefix": "10.0.0.0/16",
+ "subnetPrefix": "10.0.0.0/24",
+ "publicIPAddressType": "Dynamic",
+ "storageAccountContainerName": "vhds",
+ "storageAccountType": "Standard_LRS"
+ },
+ "resources": [
+ {
+ "type": "Microsoft.Storage/storageAccounts",
+ "name": "[variables('storageAccountName')]",
+ "apiVersion": "2015-05-01-preview",
+ "location": "[variables('location')]",
+ "properties": {
+ "accountType": "[variables('storageAccountType')]"
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/virtualNetworks",
+ "name": "[variables('virtualNetworkName')]",
+ "location": "[variables('location')]",
+ "properties": {
+ "addressSpace": {
+ "addressPrefixes": [
+ "[variables('addressPrefix')]"
+ ]
+ },
+ "subnets": [{
+ "name": "[variables('subnetName')]",
+ "properties": {
+ "addressPrefix": "[variables('subnetPrefix')]"
+ }
+ }
+ ]
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/publicIPAddresses",
+ "name": "[concat(variables('vmName'), copyIndex(), 'IPName')]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "properties": {
+ "publicIPAllocationMethod": "[variables('publicIPAddressType')]",
+ "dnsSettings": {
+ "domainNameLabel": "[concat(variables('vmName'), copyIndex())]"
+ }
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/networkInterfaces",
+ "name": "[concat(variables('vmName'), copyIndex(), 'NIC')]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "dependsOn": [
+ "[concat('Microsoft.Network/publicIPAddresses/', variables('vmName'), copyIndex(), 'IPName')]",
+ "[concat('Microsoft.Network/virtualNetworks/', variables('virtualNetworkName'))]"
+ ],
+ "properties": {
+ "ipConfigurations": [{
+ "name": "ipconfig1",
+ "properties": {
+ "privateIPAllocationMethod": "Dynamic",
+ "publicIPAddress": {
+ "id": "[resourceId('Microsoft.Network/publicIPAddresses', concat(variables('vmName'), copyIndex(), 'IPName'))]"
+ },
+ "subnet": {
+ "id": "[variables('subnetRef')]"
+ }
+ }
+ }]
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Compute/virtualMachines",
+ "name": "[concat(variables('vmName'), copyIndex())]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "dependsOn": [
+ "[concat('Microsoft.Storage/storageAccounts/', variables('storageAccountName'))]",
+ "[concat('Microsoft.Network/networkInterfaces/', variables('vmName'), copyIndex(), 'NIC')]"
+ ],
+ "properties": {
+ "hardwareProfile": {
+ "vmSize": "[variables('vmSize')]"
+ },
+ "osProfile": {
+ "computername": "[concat(variables('vmName'), copyIndex())]",
+ "adminUsername": "[variables('adminUsername')]",
+ "adminPassword": "[variables('adminPassword')]"
+ },
+ "storageProfile": {
+ "imageReference": {
+ "publisher": "[variables('imagePublisher')]",
+ "offer": "[variables('imageOffer')]",
+ "sku": "[variables('imageSku')]",
+ "version": "latest"
+ },
+ "osDisk": {
+ "name": "osdisk",
+ "vhd": {
+ "uri": "[concat('http://',variables('storageAccountName'),'.blob.core.windows.net/',variables('storageAccountContainerName'),'/', variables('vmName'), copyIndex(), 'OSDisk.vhd')]"
+ },
+ "caching": "ReadWrite",
+ "createOption": "FromImage"
+ }
+ },
+ "networkProfile": {
+ "networkInterfaces": [{
+ "id": "[resourceId('Microsoft.Network/networkInterfaces', concat(variables('vmName'), copyIndex(), 'NIC'))]"
+ }]
+ }
+ }
+ }]
+}
\ No newline at end of file
diff --git a/src/main/resources/referenceImageTemplateWithScript.json b/src/main/resources/referenceImageTemplateWithScript.json
new file mode 100644
index 0000000..5693de3
--- /dev/null
+++ b/src/main/resources/referenceImageTemplateWithScript.json
@@ -0,0 +1,172 @@
+{
+ "$schema": "http://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json",
+ "contentVersion": "1.0.0.0",
+ "parameters": {
+ "storageAccountKey" : {
+ "type" : "secureString"
+ }
+ },
+ "variables": {
+ "virtualNetworkName": "jenkinsarm-vnet",
+ "subnetName": "jenkinsarm-snet",
+ "storageAccountName": "jenkinsarmst",
+ "vnetID": "[resourceId('Microsoft.Network/virtualNetworks', variables('virtualNetworkName'))]",
+ "subnetRef": "[concat(variables('vnetID'),'/subnets/',variables('subnetName'))]",
+ "addressPrefix": "10.0.0.0/16",
+ "subnetPrefix": "10.0.0.0/24",
+ "publicIPAddressType": "Dynamic",
+ "storageAccountContainerName": "vhds",
+ "storageAccountType": "Standard_LRS",
+ "startupScriptURI": "",
+ "startupScriptName": "",
+ "jenkinsServerURL": "",
+ "clientSecrets": []
+ },
+ "resources": [
+ {
+ "type": "Microsoft.Storage/storageAccounts",
+ "name": "[variables('storageAccountName')]",
+ "apiVersion": "2015-05-01-preview",
+ "location": "[variables('location')]",
+ "properties": {
+ "accountType": "[variables('storageAccountType')]"
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/virtualNetworks",
+ "name": "[variables('virtualNetworkName')]",
+ "location": "[variables('location')]",
+ "properties": {
+ "addressSpace": {
+ "addressPrefixes": [
+ "[variables('addressPrefix')]"
+ ]
+ },
+ "subnets": [{
+ "name": "[variables('subnetName')]",
+ "properties": {
+ "addressPrefix": "[variables('subnetPrefix')]"
+ }
+ }
+ ]
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/publicIPAddresses",
+ "name": "[concat(variables('vmName'), copyIndex(), 'IPName')]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "properties": {
+ "publicIPAllocationMethod": "[variables('publicIPAddressType')]",
+ "dnsSettings": {
+ "domainNameLabel": "[concat(variables('vmName'), copyIndex())]"
+ }
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Network/networkInterfaces",
+ "name": "[concat(variables('vmName'), copyIndex(), 'NIC')]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "dependsOn": [
+ "[concat('Microsoft.Network/publicIPAddresses/', variables('vmName'), copyIndex(), 'IPName')]",
+ "[concat('Microsoft.Network/virtualNetworks/', variables('virtualNetworkName'))]"
+ ],
+ "properties": {
+ "ipConfigurations": [{
+ "name": "ipconfig1",
+ "properties": {
+ "privateIPAllocationMethod": "Dynamic",
+ "publicIPAddress": {
+ "id": "[resourceId('Microsoft.Network/publicIPAddresses', concat(variables('vmName'), copyIndex(), 'IPName'))]"
+ },
+ "subnet": {
+ "id": "[variables('subnetRef')]"
+ }
+ }
+ }]
+ }
+ },
+ {
+ "apiVersion": "2015-05-01-preview",
+ "type": "Microsoft.Compute/virtualMachines",
+ "name": "[concat(variables('vmName'), copyIndex())]",
+ "location": "[variables('location')]",
+ "copy": {
+ "name": "vmcopy",
+ "count": "[parameters('count')]"
+ },
+ "dependsOn": [
+ "[concat('Microsoft.Storage/storageAccounts/', variables('storageAccountName'))]",
+ "[concat('Microsoft.Network/networkInterfaces/', variables('vmName'), copyIndex(), 'NIC')]"
+ ],
+ "properties": {
+ "hardwareProfile": {
+ "vmSize": "[variables('vmSize')]"
+ },
+ "osProfile": {
+ "computername": "[concat(variables('vmName'), copyIndex())]",
+ "adminUsername": "[variables('adminUsername')]",
+ "adminPassword": "[variables('adminPassword')]"
+ },
+ "storageProfile": {
+ "imageReference": {
+ "publisher": "[variables('imagePublisher')]",
+ "offer": "[variables('imageOffer')]",
+ "sku": "[variables('imageSku')]",
+ "version": "latest"
+ },
+ "osDisk": {
+ "name": "osdisk",
+ "vhd": {
+ "uri": "[concat('http://',variables('storageAccountName'),'.blob.core.windows.net/',variables('storageAccountContainerName'),'/', variables('vmName'), copyIndex(), 'OSDisk.vhd')]"
+ },
+ "caching": "ReadWrite",
+ "createOption": "FromImage"
+ }
+ },
+ "networkProfile": {
+ "networkInterfaces": [{
+ "id": "[resourceId('Microsoft.Network/networkInterfaces', concat(variables('vmName'), copyIndex(), 'NIC'))]"
+ }]
+ }
+ },
+ "resources" : [
+ {
+ "type": "extensions",
+ "name": "[concat('customScript', variables('vmName'), copyIndex())]",
+ "apiVersion": "2015-05-01-preview",
+ "location": "[variables('location')]",
+ "dependsOn": [
+ "[concat('Microsoft.Compute/virtualMachines/', variables('vmName'), copyIndex())]"
+ ],
+ "properties": {
+ "publisher": "Microsoft.Compute",
+ "type": "CustomScriptExtension",
+ "typeHandlerVersion": "1.7",
+ "autoUpgradeMinorVersion": true,
+ "settings": {
+ "fileUris": [
+ "[variables('startupScriptURI')]"
+ ],
+ "commandToExecute": "[concat('powershell.exe -ExecutionPolicy Unrestricted -File ', variables('startupScriptName'),' ', variables('jenkinsServerURL'),' ', variables('vmName'),copyIndex(),' ', variables('clientSecrets')[copyIndex()])]"
+ },
+ "protectedSettings": {
+ "storageAccountName" : "[variables('storageAccountName')]",
+ "storageAccountKey" : "[parameters('storageAccountKey')]"
+ }
+ }
+ }
+ ]
+ }
+ ]
+}
\ No newline at end of file
diff --git a/src/main/resources/scripts/azure.ps1 b/src/main/resources/scripts/azure.ps1
deleted file mode 100644
index f01d1d8..0000000
--- a/src/main/resources/scripts/azure.ps1
+++ /dev/null
@@ -1,62 +0,0 @@
-Set-ExecutionPolicy Unrestricted
-$jenkinsServerUrl = $args[0]
-$vmName = $args[1]
-$secret = $args[2]
-
-$jenkinsSlaveJarUrl = $jenkinsServerUrl + "jnlpJars/slave.jar"
-$jnlpUrl=$jenkinsServerUrl + 'computer/' + $vmName + '/slave-agent.jnlp'
-
-$baseDir = 'c:\azurecsdir'
-$JDKUrl = 'http://azure.azulsystems.com/zulu/zulu1.7.0_51-7.3.0.4-win64.zip?jenkins'
-$destinationJDKZipPath = $baseDir + '\zuluJDK.zip'
-$destinationSlaveJarPath = $baseDir + '\slave.jar'
-$javaExe = $baseDir + '\zulu1.7.0_51-7.3.0.4-win64\bin\java.exe'
-
-# Function to get path of script file
-function Get-ScriptPath
-{
- return $MyInvocation.ScriptName;
-}
-
-# Checking if this is first time script is getting executed, if yes then downloading JDK
-If(-not((Test-Path $destinationJDKZipPath)))
-{
- md -Path $baseDir -Force
- $wc = New-Object System.Net.WebClient
- $wc.DownloadFile($JDKUrl, $destinationJDKZipPath)
-
- $shell_app = new-object -com shell.application
- $zip_file = $shell_app.namespace($destinationJDKZipPath)
- $javaInstallDir = $shell_app.namespace($baseDir)
- $javaInstallDir.Copyhere($zip_file.items())
-
- $wc = New-Object System.Net.WebClient
- $wc.DownloadFile($jenkinsSlaveJarUrl, $destinationSlaveJarPath)
-
- $scriptPath = Get-ScriptPath
- $content = 'powershell.exe -ExecutionPolicy Unrestricted -file' + ' '+ $scriptPath + ' '+ $jenkinsServerUrl + ' ' + $vmName + ' ' + $secret
- $commandFile = $baseDir + '\slaveagenttask.cmd'
- $content | Out-File $commandFile -Encoding ASCII -Append
- schtasks /create /tn "Jenkins slave agent" /ru "SYSTEM" /sc onstart /rl HIGHEST /delay 0000:30 /tr $commandFile /f
-}
-
-# Launching jenkins slave agent
-$process = New-Object System.Diagnostics.Process;
-$process.StartInfo.FileName = $javaExe;
-If($secret)
-{
- $process.StartInfo.Arguments = "-jar $destinationSlaveJarPath -secret $secret -jnlpUrl $jnlpUrl"
-}
-else
-{
- $process.StartInfo.Arguments = "-jar $destinationSlaveJarPath -jnlpUrl $jnlpUrl"
-}
-$process.StartInfo.RedirectStandardError = $true;
-$process.StartInfo.RedirectStandardOutput = $true;
-$process.StartInfo.UseShellExecute = $false;
-$process.StartInfo.CreateNoWindow = $true;
-
-$process.StartInfo;
-$process.Start();
-
-Write-Host 'Done Init Script.';
diff --git a/src/main/resources/scripts/init.ps1 b/src/main/resources/scripts/init.ps1
new file mode 100644
index 0000000..bcb4048
--- /dev/null
+++ b/src/main/resources/scripts/init.ps1
@@ -0,0 +1,41 @@
+Set-ExecutionPolicy Unrestricted
+$jenkinsServerUrl = $args[0]
+$vmName = $args[1]
+$secret = $args[2]
+
+$baseDir = 'C:\Jenkins'
+mkdir $baseDir
+# Download the JDK
+$source = "http://download.oracle.com/otn-pub/java/jdk/7u79-b15/jdk-7u79-windows-x64.exe"
+$destination = "$baseDir\jdk.exe"
+$client = new-object System.Net.WebClient
+$cookie = "oraclelicense=accept-securebackup-cookie"
+$client.Headers.Add([System.Net.HttpRequestHeader]::Cookie, $cookie)
+$client.downloadFile([string]$source, [string]$destination)
+
+# Execute the unattended install
+$jdkInstallDir=$baseDir + '\jdk\'
+$jreInstallDir=$baseDir + '\jre\'
+C:\Jenkins\jdk.exe /s INSTALLDIR=$jdkInstallDir /INSTALLDIRPUBJRE=$jdkInstallDir
+
+$javaExe=$jdkInstallDir + '\bin\java.exe'
+$jenkinsSlaveJarUrl = $jenkinsServerUrl + "jnlpJars/slave.jar"
+$destinationSlaveJarPath = $baseDir + '\slave.jar'
+
+# Download the jar file
+$client = new-object System.Net.WebClient
+$client.DownloadFile($jenkinsSlaveJarUrl, $destinationSlaveJarPath)
+
+# Calculate the jnlpURL
+$jnlpUrl = $jenkinsServerUrl + 'computer/' + $vmName + '/slave-agent.jnlp'
+
+while ($true) {
+ try {
+ # Launch
+ & $javaExe -jar $destinationSlaveJarPath -secret $secret -jnlpUrl $jnlpUrl -noReconnect
+ }
+ catch [System.Exception] {
+ Write-Output $_.Exception.ToString()
+ }
+ sleep 10
+}
\ No newline at end of file
diff --git a/src/main/resources/templateImageValue.json b/src/main/resources/templateImageValue.json
deleted file mode 100644
index 94f2338..0000000
--- a/src/main/resources/templateImageValue.json
+++ /dev/null
@@ -1,135 +0,0 @@
-{
- "$schema": "http://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json",
- "contentVersion": "1.0.0.0",
- "parameters": {
- },
- "variables": {
- "virtualNetworkName": "jenkinsarm-vnet",
- "subnetName": "jenkinsarm-snet",
- "storageAccountName": "jenkinsarmst",
- "vnetID": "[resourceId('Microsoft.Network/virtualNetworks', variables('virtualNetworkName'))]",
- "subnetRef": "[concat(variables('vnetID'),'/subnets/',variables('subnetName'))]",
- "addressPrefix": "10.0.0.0/16",
- "subnetPrefix": "10.0.0.0/24",
- "publicIPAddressType": "Dynamic",
- "storageAccountContainerName": "vhds",
- "storageAccountType": "Standard_LRS"
- },
- "resources": [
- {
- "type": "Microsoft.Storage/storageAccounts",
- "name": "[variables('storageAccountName')]",
- "apiVersion": "2015-05-01-preview",
- "location": "[variables('location')]",
- "properties": {
- "accountType": "[variables('storageAccountType')]"
- }
- },
- {
- "apiVersion": "2015-05-01-preview",
- "type": "Microsoft.Network/virtualNetworks",
- "name": "[variables('virtualNetworkName')]",
- "location": "[variables('location')]",
- "properties": {
- "addressSpace": {
- "addressPrefixes": [
- "[variables('addressPrefix')]"
- ]
- },
- "subnets": [{
- "name": "[variables('subnetName')]",
- "properties": {
- "addressPrefix": "[variables('subnetPrefix')]"
- }
- }
- ]
- }
- },
- {
- "apiVersion": "2015-05-01-preview",
- "type": "Microsoft.Network/publicIPAddresses",
- "name": "[concat(variables('vmName'), copyIndex(), 'IPName')]",
- "location": "[variables('location')]",
- "copy": {
- "name": "vmcopy",
- "count": "[parameters('count')]"
- },
- "properties": {
- "publicIPAllocationMethod": "[variables('publicIPAddressType')]",
- "dnsSettings": {
- "domainNameLabel": "[concat(variables('vmName'), copyIndex())]"
- }
- }
- },
- {
- "apiVersion": "2015-05-01-preview",
- "type": "Microsoft.Network/networkInterfaces",
- "name": "[concat(variables('vmName'), copyIndex(), 'NIC')]",
- "location": "[variables('location')]",
- "copy": {
- "name": "vmcopy",
- "count": "[parameters('count')]"
- },
- "dependsOn": [
- "[concat('Microsoft.Network/publicIPAddresses/', variables('vmName'), copyIndex(), 'IPName')]",
- "[concat('Microsoft.Network/virtualNetworks/', variables('virtualNetworkName'))]"
- ],
- "properties": {
- "ipConfigurations": [{
- "name": "ipconfig1",
- "properties": {
- "privateIPAllocationMethod": "Dynamic",
- "publicIPAddress": {
- "id": "[resourceId('Microsoft.Network/publicIPAddresses', concat(variables('vmName'), copyIndex(), 'IPName'))]"
- },
- "subnet": {
- "id": "[variables('subnetRef')]"
- }
- }
- }]
- }
- },
- {
- "apiVersion": "2015-05-01-preview",
- "type": "Microsoft.Compute/virtualMachines",
- "name": "[concat(variables('vmName'), copyIndex())]",
- "location": "[variables('location')]",
- "copy": {
- "name": "vmcopy",
- "count": "[parameters('count')]"
- },
- "dependsOn": [
- "[concat('Microsoft.Storage/storageAccounts/', variables('storageAccountName'))]",
- "[concat('Microsoft.Network/networkInterfaces/', variables('vmName'), copyIndex(), 'NIC')]"
- ],
- "properties": {
- "hardwareProfile": {
- "vmSize": "[variables('vmSize')]"
- },
- "osProfile": {
- "computername": "[concat(variables('vmName'), copyIndex())]",
- "adminUsername": "[variables('adminUsername')]",
- "adminPassword": "[variables('adminPassword')]"
- },
- "storageProfile": {
- "osDisk": {
- "name": "[concat(variables('vmName'), copyIndex())]",
- "osType": "[variables('osType')]",
- "caching": "ReadWrite",
- "image": {
- "uri": "[variables('image')]"
- },
- "createOption": "FromImage",
- "vhd": {
- "uri": "[concat('http://',variables('storageAccountName'),'.blob.core.windows.net/',variables('storageAccountContainerName'),'/', variables('vmName'), copyIndex(), 'OSDisk.vhd')]"
- }
- }
- },
- "networkProfile": {
- "networkInterfaces": [{
- "id": "[resourceId('Microsoft.Network/networkInterfaces', concat(variables('vmName'), copyIndex(), 'NIC'))]"
- }]
- }
- }
- }]
-}
\ No newline at end of file
diff --git a/src/main/resources/templateValue.json b/src/main/resources/templateValue.json
deleted file mode 100644
index 3d660b9..0000000
--- a/src/main/resources/templateValue.json
+++ /dev/null
@@ -1,137 +0,0 @@
-{
- "$schema": "http://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json",
- "contentVersion": "1.0.0.0",
- "parameters": {
- },
- "variables": {
- "virtualNetworkName": "jenkinsarm-vnet",
- "subnetName": "jenkinsarm-snet",
- "storageAccountName": "jenkinsarmst",
- "vnetID": "[resourceId('Microsoft.Network/virtualNetworks', variables('virtualNetworkName'))]",
- "subnetRef": "[concat(variables('vnetID'),'/subnets/',variables('subnetName'))]",
- "addressPrefix": "10.0.0.0/16",
- "subnetPrefix": "10.0.0.0/24",
- "publicIPAddressType": "Dynamic",
- "storageAccountContainerName": "vhds",
- "storageAccountType": "Standard_LRS"
- },
- "resources": [
- {
- "type": "Microsoft.Storage/storageAccounts",
- "name": "[variables('storageAccountName')]",
- "apiVersion": "2015-05-01-preview",
- "location": "[variables('location')]",
- "properties": {
- "accountType": "[variables('storageAccountType')]"
- }
- },
- {
- "apiVersion": "2015-05-01-preview",
- "type": "Microsoft.Network/virtualNetworks",
- "name": "[variables('virtualNetworkName')]",
- "location": "[variables('location')]",
- "properties": {
- "addressSpace": {
- "addressPrefixes": [
- "[variables('addressPrefix')]"
- ]
- },
- "subnets": [{
- "name": "[variables('subnetName')]",
- "properties": {
- "addressPrefix": "[variables('subnetPrefix')]"
- }
- }
- ]
- }
- },
- {
- "apiVersion": "2015-05-01-preview",
- "type": "Microsoft.Network/publicIPAddresses",
- "name": "[concat(variables('vmName'), copyIndex(), 'IPName')]",
- "location": "[variables('location')]",
- "copy": {
- "name": "vmcopy",
- "count": "[parameters('count')]"
- },
- "properties": {
- "publicIPAllocationMethod": "[variables('publicIPAddressType')]",
- "dnsSettings": {
- "domainNameLabel": "[concat(variables('vmName'), copyIndex())]"
- }
- }
- },
- {
- "apiVersion": "2015-05-01-preview",
- "type": "Microsoft.Network/networkInterfaces",
- "name": "[concat(variables('vmName'), copyIndex(), 'NIC')]",
- "location": "[variables('location')]",
- "copy": {
- "name": "vmcopy",
- "count": "[parameters('count')]"
- },
- "dependsOn": [
- "[concat('Microsoft.Network/publicIPAddresses/', variables('vmName'), copyIndex(), 'IPName')]",
- "[concat('Microsoft.Network/virtualNetworks/', variables('virtualNetworkName'))]"
- ],
- "properties": {
- "ipConfigurations": [{
- "name": "ipconfig1",
- "properties": {
- "privateIPAllocationMethod": "Dynamic",
- "publicIPAddress": {
- "id": "[resourceId('Microsoft.Network/publicIPAddresses', concat(variables('vmName'), copyIndex(), 'IPName'))]"
- },
- "subnet": {
- "id": "[variables('subnetRef')]"
- }
- }
- }]
- }
- },
- {
- "apiVersion": "2015-05-01-preview",
- "type": "Microsoft.Compute/virtualMachines",
- "name": "[concat(variables('vmName'), copyIndex())]",
- "location": "[variables('location')]",
- "copy": {
- "name": "vmcopy",
- "count": "[parameters('count')]"
- },
- "dependsOn": [
- "[concat('Microsoft.Storage/storageAccounts/', variables('storageAccountName'))]",
- "[concat('Microsoft.Network/networkInterfaces/', variables('vmName'), copyIndex(), 'NIC')]"
- ],
- "properties": {
- "hardwareProfile": {
- "vmSize": "[variables('vmSize')]"
- },
- "osProfile": {
- "computername": "[concat(variables('vmName'), copyIndex())]",
- "adminUsername": "[variables('adminUsername')]",
- "adminPassword": "[variables('adminPassword')]"
- },
- "storageProfile": {
- "imageReference": {
- "publisher": "[variables('imagePublisher')]",
- "offer": "[variables('imageOffer')]",
- "sku": "[variables('imageSku')]",
- "version": "latest"
- },
- "osDisk": {
- "name": "osdisk",
- "vhd": {
- "uri": "[concat('http://',variables('storageAccountName'),'.blob.core.windows.net/',variables('storageAccountContainerName'),'/', variables('vmName'), copyIndex(), 'OSDisk.vhd')]"
- },
- "caching": "ReadWrite",
- "createOption": "FromImage"
- }
- },
- "networkProfile": {
- "networkInterfaces": [{
- "id": "[resourceId('Microsoft.Network/networkInterfaces', concat(variables('vmName'), copyIndex(), 'NIC'))]"
- }]
- }
- }
- }]
-}
\ No newline at end of file
diff --git a/src/main/webapp/help-doNotUseMachineIfInitFails.html b/src/main/webapp/help-doNotUseMachineIfInitFails.html
new file mode 100644
index 0000000..dcc77ee
--- /dev/null
+++ b/src/main/webapp/help-doNotUseMachineIfInitFails.html
@@ -0,0 +1,4 @@
+
+ If checked, the Azure node will execute the startup script as root.
+ Currently applies to Linux nodes only.
+
diff --git a/src/main/webapp/help-executeInitScriptAsRoot.html b/src/main/webapp/help-executeInitScriptAsRoot.html
new file mode 100644
index 0000000..b67e8d8
--- /dev/null
+++ b/src/main/webapp/help-executeInitScriptAsRoot.html
@@ -0,0 +1,4 @@
+
+ If checked, the Azure node will be discarded if the initialization script returns a non-zero exit code.
+ Currently applies to Linux nodes only.
+
diff --git a/src/main/webapp/help-initScript.html b/src/main/webapp/help-initScript.html
index 6e31dc6..e672d25 100644
--- a/src/main/webapp/help-initScript.html
+++ b/src/main/webapp/help-initScript.html
@@ -1,19 +1,22 @@
-
At a minimum, the init script needs to install a Java runtime.
+
At a minimum, the init script needs to install a Java runtime.
Custom prepared images are recommended if the initialization script is taking more than 20 minutes to execute.
-Below are examples of initialization scripts:
+Below are examples of initialization scripts:
1)
Ubuntu
# Install Java
sudo apt-get -y update
sudo apt-get install -y openjdk-7-jdk
sudo apt-get -y update --fix-missing
sudo apt-get install -y openjdk-7-jdk
-2) For Windows slaves with JNLP launch, if no init script is provided then Jenkins will execute the default PowerShell script,
- which will work only if anonymous access is allowed for the master machine.
-
- If your master machine is configured with security options, refer to this script:
-
https://gist.github.com/snallami/5aa9ea2c57836a3b3635
- and edit it accordingly.
+2)
Windows w/JNLP
+ For Windows slaves with JNLP launch, this script is a powershell script.
+ Automatically passed to this script is:
+ First argument - Jenkins server URL
+ Second argument - VMName
+ Third argument - JNLP secret, required if the server has security enabled.
+ You need to install Java, download the slave jar file from: '[server url]jnlpJars/slave.jar'.
+ The server url should already have a trailing slash. Then execute the following to connect:
+ java.exe -jar [slave jar location] [-secret [client secret if required]] [server url]computer/[vm name]/slave-agent.jnlp
diff --git a/src/main/webapp/help-maxVirtualMachinesLimit.html b/src/main/webapp/help-maxVirtualMachinesLimit.html
index 4f6dd68..4551ea4 100644
--- a/src/main/webapp/help-maxVirtualMachinesLimit.html
+++ b/src/main/webapp/help-maxVirtualMachinesLimit.html
@@ -1,6 +1,6 @@
-Specify the maximum number of virtual machines that can be created in a subscription.
+Specify the maximum number of virtual machines that can be created.
-This includes the number of virtual machines that were created outside Jenkins.
+This number only includes those machines that the current set of credentials has access to view and does NOT include classic VMs.
diff --git a/src/main/webapp/help-templateDisabled.html b/src/main/webapp/help-templateDisabled.html
new file mode 100644
index 0000000..e44cf06
--- /dev/null
+++ b/src/main/webapp/help-templateDisabled.html
@@ -0,0 +1,3 @@
+
+If checked, no attempt will be made to allocate this template.
+
diff --git a/src/main/webapp/help-templateStatus.html b/src/main/webapp/help-templateStatus.html
deleted file mode 100644
index 9e6415d..0000000
--- a/src/main/webapp/help-templateStatus.html
+++ /dev/null
@@ -1,11 +0,0 @@
-
-If set to "Active until first failure", Jenkins will keep attempting to create slaves from the template during the job execution until the first unrecoverable error
-is encountered, at which point this setting will be automatically changed to "Disabled".
-
-If set to "Disabled", the creation of slaves based on this template will be suspended.
-
-If set to "Active always", Jenkins will continue attempting to provision slaves based on this template regardless of any failures that may occur. Note that this setting may
-result in an excessive allocation of resources for the malfunctioning slaves. Such a continuous slave provisioning process can be stopped manually by changing the slave
-provisioning setting to "Disabled", or fixing the underlying issue causing the failures.
-
-