Deploying Virtual Machines in Azure using Service Manager and SMA Part III
This is the 3rd post in a 3-part series on deploying VMs in Azure using System Center Service Manager and Service Management Automation (SMA). In this post we’ll cover using the Service Manager Self-Service Portal to trigger an SMA Runbook which deploys a new VM in Azure.
Part I: Preparing your VM for upload, uploading it to Azure, and configuring Azure
Part II: Deploying your VM in PowerShell and SMA
Part III: Deploying your VM using the Service Manager Self-Service Portal
Summary
In Part I we uploaded a custom image to Azure and in Part II we created an SMA Runbook to deploy a new virtual machine using that image. The steps below will take you through configuring System Center Service Manager to launch an SMA Runbook which will deploy a Virtual Machine in Azure.
Prerequisites
- Install the Service Manager Authoring Tool on a workstation
- Install Windows Azure PowerShell on the machine where your SMA Runbook will be launched (configured in Part II)
- Install the Service Manager Console on the machine where your SMA Runbook will be launched.
- Install SMA PowerShell on the Service Manager Management Server where the workflow will be run. You can install this from the Orchestrator installation CD, just launch setup and it’s on the bottom.
- Add the workflow account in Service Manager to the smaAdminGroup (local group) on the SMA Server. You can get this account by opening the Service Manager console and going to Administration\Security\Run As Accounts\Workflow Account.
- Download the Azure Settings File and place it somewhere on the SMA Server. In order for scripts to connect to Azure we need to download an Azure settings file for authentication. You can download this file from the following URL: https://windows.azure.com/download/publishprofile.aspx.
- Get all of the parameters needed to execute the SMA Runbook manually through SMA. Part II has steps to get these.
Modify the SMA Runbook
The SMA Runbook we created in Part II will mostly work as-is but we’ll want to make several modifications so it works better with Service Manager. The main modification adds to the end of the script so that it will set the Service Manager activity to Completed. If we don’t do this the Virtual Machine will get deployed but the Service Request will remain In Progress. If you plan on using the SMA Runbook without Service Manager then instead of modifying the existing one you can create a new one.
- Logon to the Service Management Portal and click on Automation\Runbooks
- Scroll down to the DeployVMInAzure Runbook and select it
- Click Author, Draft, and Edit Runbook
- Replace the script with the one below
workflow DeployVMInAzure
{
param(
$azureSettingsFile,
$azureAccountName,
$imageName,
$vmName,
$instanceSize,
$adminUserName,
$adminPassword,
$domain,
$domainUserName,
$domainPassword,
$affinityGroup,
$networkName,
$azureStorageAccountName,
$subnetName,
$activityID,
$smManagementServer
)
#Set Instance Size
if ($instanceSize -eq "A0") { $instanceSize = 'ExtraSmall' }
elseif ($instanceSize -eq "A1") { $instanceSize = 'Small' }
elseif ($instanceSize -eq "A2") { $instanceSize = 'Medium' }
elseif ($instanceSize -eq "A3") { $instanceSize = 'Large' }
elseif ($instanceSize -eq "A4") { $instanceSize = 'ExtraLarge' }
inlinescript
{
#Import Azure PowerShell Module
Import-Module Azure
#Remove Existing Azure Sessions
Remove-AzureAccount -Name $Using:azureAccountName -Force
#Import Azure Settings File
Import-AzurePublishSettingsFile -PublishSettingsFile ($Using:azureSettingsFile).Replace("\\","\")
#Set Azure Subscription
Get-AzureSubscription | Set-AzureSubscription -currentstorageaccountname $Using:azureStorageAccountName
#Increment VM Name
$i = 0
foreach ($vm in Get-AzureVM)
{
if ($vm.InstanceName.Contains($Using:vmName))
{
[int]$increment = $vm.InstanceName.SubString($Using:vmName.Length)
if ($increment -gt $i) { $i = $increment }
}
}
$i++
$vmName = $Using:vmName + $i
#Create New Azure Cloud Service
New-AzureService -ServiceName $vmName -AffinityGroup $Using:affinityGroup
#Create Azure VM
if ($Using:domain)
{
New-AzureVMConfig -Name $vmName -InstanceSize $Using:instanceSize -ImageName $Using:imageName |
Add-AzureProvisioningConfig -WindowsDomain -Password $Using:adminPassword -JoinDomain $Using:domain -Domain $Using:domain -DomainUserName $Using:domainUserName -DomainPassword $Using:domainPassword -AdminUsername $Using:adminUserName |
Set-AzureSubnet $Using:subnetName |
New-AzureVM -ServiceName $vmName -VNetName $Using:networkName
}
else
{
New-AzureVMConfig -Name $vmName -InstanceSize $Using:instanceSize -ImageName $Using:imageName |
Add-AzureProvisioningConfig -Windows -AdminUsername $Using:adminUserName -Password $Using:adminPassword |
Set-AzureSubnet $Using:subnetName |
New-AzureVM -ServiceName $vmName -VNetName $Using:networkName
}
#Set SM Activity to Completed
if ($Using:activityID)
{
#Connect to SM
$smDir = (Get-ItemProperty 'hklm:/software/microsoft/System Center/2010/Service Manager/Setup').InstallDirectory
Import-Module ($smDir + "\Powershell\System.Center.Service.Manager.psd1")
$sm = New-SCManagementGroupConnection -computerName $Using:smManagementServer
#Get SM Class
$class = Get-SCClass -name 'Custom.Example.Azure.DeployVM'
#Get SM Class Instance
$instance = Get-SCClassInstance -class $class -filter ('Id -eq {0}' -f $Using:activityID)
#Update Activity to Completed
$instance.Status = "ActivityStatusEnum.Completed"
Update-SCSMClassInstance -Instance $instance
}
}
}
- Publish the Runbook
Create a Management Pack in the Authoring Tool
Launch the Service Manager Authoring Tool
Select File\New, and name your MP Custom.Example.Azure.xml
Under Custom.Example.Azure, right-click on Classes and choose Create other class…
- For Base class, choose Activity and click OK
- For Internal name type Custom.Example.Azure.DeployVM and click Create
Under your new class, delete the Property_xx property (mine is Property_33)
Create the following String properties for you Custom.Example.Azure.DeployVMclass
- WebServiceEndPoint
- SMARunbookName
- azureSettingsFile
- azureAccountName
- imageName
- vmName
- instanceSize
- adminUserName
- adminPassword
- domain
- domainUserName
- domainPassword
- affinityGroup
- networkName
- azureStorageAccountName
- subnetName
- smManagementServer
Under Custom.Example.Azure, right-click on Workflows and choose Create
Under Name type DeployVM and click Next
Under Trigger Condition choose Run only when a database object meets specified conditions and click Next
Under Trigger Criteria choose the Custom.Example.Azure.DeployVM class, choose When a object of the selected class is updated, and click Additional Criteria
- Select Changed To and set a Criteria of Status equals In Progress
- Click OK, Create, and Close
- The Workflow Designer should open along with an Activities Toolbox. Drag the Windows PowerShell Script Activity into the Workflow
- Select the windowsPowerShellScript1 activity and then click on the ellipsis next to Script Body under Details
- Paste the following script into the Script Body window
Start-SmaRunbook -WebServiceEndpoint $WebServiceEndpoint -Name $SMARunbookName -Parameters @{"azureSettingsFile" = "$azureSettingsFile"; "azureAccountName" = "$azureAccountName"; "imageName" = "$imageName"; "vmName" = "$vmName"; "instanceSize" = "$instanceSize"; "adminUserName" = "$adminUserName"; "adminPassword" = "$adminPassword"; "domain" = "$domain"; "domainUserName" = "$domainUserName"; "domainPassword" = "$domainPassword"; "affinityGroup" = "$affinityGroup"; "networkName" = "$networkName"; "azureStorageAccountName" = "$azureStorageAccountName"; "subnetName" = "$subnetName"; "smManagementServer" = "$smManagementServer"; "activityID" = "$activityID"}
Click on Script Properties and Add the following properties to the Activity (Click Use a class property to find the matching class property) and click OK
- WebServiceEndPoint
- SMARunbookName
- azureSettingsFile
- azureAccountName
- imageName
- vmName
- instanceSize
- adminUserName
- adminPassword
- domain
- domainUserName
- domainPassword
- affinityGroup
- networkName
- azureStorageAccountName
- subnetName
- smManagementServer
- activityID (maps to ID)
- Save the Management Pack in the Authoring Tool
- Copy the DeployVM.dll file from your management pack folder to your Service Manager Management Server folder (\Program Files\Microsoft System Center 2012 R2\Service Manager) and restart the Microsoft Monitoring Agent service on the Service Manager Management Server.
- Restart your Service Manager Console if you had it open
Import the Management Pack in Service Manager
- Open the Service Manager Console and go to Administration\Management Packs
- Right-click on Management Packs and choose Import
- Select the Custom.Example.Azure management pack, click Open, Import, and OK
Create a new Template for the Custom.Example.Azure.DeployVM Class
Open the Service Manager Console and go to Library\Templates
Right-click on Templates and select Create Template
- For Name, type Deploy Azure VM Template
- For Class, choose Custom.Example.Azure.DeployVM
- Click OK
Fill in the following properties of the form based on the parameters used running the SMA Runbook manually
Display Name: Deploy Azure VM
Title: Deploy Azure VM
WebServiceEndPoint (your SMA Server): https://mysmaserver.contoso.com
SMARunbookName: DeployVMInAzure
azureSettingsFile: c:\temp\myAzureSettings.publishsettings
azureAccountName: myAzureAccount@myemailaccount.com
imageName: w2012r2base3
vmName: rslatenTest
instanceSize: A0
adminUserName: rslaten
adminPassword: <P@$$W0Rd1>
domain: contoso.com
domainUserName: rslaten
domainPassword: <P@$$W0Rd1>
affinityGroup: Lab
networkName: Lab
azureStorageAccountName: rslaten
subnetName: Subnet-1
smManagementServer: sm1.contoso.com
Click OK
Create a Service Request Template
Open the Service Manager Console and go to Library\Templates
Right-click on Templates and select Create Template
- For Name, type Deploy Azure VM Service Request Template
- For Class, choose Service Request
- Change the Management Pack to Custom.Example.Azure
- Click OK
Enter a Title: Deploy Azure VM Service Request
Click the Activities tab and click the Plus sign
Select the Deploy Azure VM Template, click OK, and click OK
Create a Request Offering
In this request offering I’m only going to let the user select the instance size. With additional customization you can, however, allow other selections such as VM Name, Image Name, etc…
- Open the Service Manager Console and go to Library\Request Offerings and click Create Request Offering
- Click Next and enter Deploy Azure Virtual Machine for the Title
- Select the Deploy Azure VM Service Request Template and click OK
- Under User Prompts type Instance Size with a type of Simple List and click Next
- Under Configure Prompts select Instance Size and click Configure
- Enter the following list properties for instance size (A0 – A9)
- Click OK
- Click Next
- Under Map Prompts select Custom.Example.Azure.DeployVM
- Map InstanceSize to InstanceSize:ListValue
- Click Next, Click Next
- Under Publish change Offering Status to Published and click Next
- Click Create and Close
Create a Service Offering
- Open the Service Manager Console and go to Library\Service Offerings and click Create Service Offering
- Click Next, enter Cloud Offerings for Title, Click Next 3 Times
- Under Request Offering Add the Deploy Azure Virtual Machine request offering, click OK, and click Next
- Under Publish change the Offering Status to Published and click Next
- Click Create and Close
The output from the exported Management Pack is below:
<ManagementPack ContentReadable="true" SchemaVersion="2.0" OriginalSchemaVersion="1.1" xmlns:xsd="https://www.w3.org/2001/XMLSchema" xmlns:xsl="https://www.w3.org/1999/XSL/Transform">
<Manifest>
<Identity>
<ID>Custom.Example.Azure</ID>
<Version>1.0.0.0</Version>
</Identity>
<Name>Custom.Example.Azure</Name>
<References>
<Reference Alias="System">
<ID>System.Library</ID>
<Version>7.5.8501.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="Console">
<ID>Microsoft.EnterpriseManagement.ServiceManager.UI.Console</ID>
<Version>7.5.3079.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="Alias_952b56e8_dd9f_480c_8f57_1d53f5894aca">
<ID>System.WorkItem.Activity.Library</ID>
<Version>7.5.3079.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="EnterpriseManagement">
<ID>Microsoft.EnterpriseManagement.ServiceManager.UI.Administration</ID>
<Version>7.5.3079.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="SystemCenter">
<ID>Microsoft.SystemCenter.Library</ID>
<Version>7.0.8433.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="SystemCenter1">
<ID>Microsoft.SystemCenter.Subscriptions</ID>
<Version>7.5.3079.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="Core">
<ID>ServiceManager.Core.Library</ID>
<Version>7.5.3079.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="Windows">
<ID>Microsoft.Windows.Library</ID>
<Version>7.5.8501.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="System_WorkItem_Library">
<ID>System.WorkItem.Library</ID>
<Version>7.5.3079.0</Version>
<PublicKeyToken>31bf3856ad364e35</PublicKeyToken>
</Reference>
<Reference Alias="Example">
<ID>Custom.Example.ServiceRequestExtended</ID>
<Version>1.0.0.1</Version>
<PublicKeyToken>e24f5efd5fd6e660</PublicKeyToken>
</Reference>
</References>
</Manifest>
<TypeDefinitions>
<EntityTypes>
<ClassTypes>
<ClassType ID="Custom.Example.Azure.DeployVM" Accessibility="Public" Abstract="false" Base="Alias_952b56e8_dd9f_480c_8f57_1d53f5894aca!System.WorkItem.Activity" Hosted="false" Singleton="false" Extension="false">
<Property ID="WebServiceEndpoint" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="azureSettingsFile" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="imageName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="vmName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="instanceSize" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="adminUserName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="adminPassword" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="domain" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="domainUserName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="domainPassword" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="affinityGroup" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="networkName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="azureStorageAccountName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="subnetName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="SMARunbookName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="azureAccountName" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
<Property ID="smManagementServer" Type="string" AutoIncrement="false" Key="false" CaseSensitive="false" MaxLength="256" MinLength="0" Required="false" Scale="0" />
</ClassType>
</ClassTypes>
</EntityTypes>
<ModuleTypes>
<WriteActionModuleType ID="DeployVM.WindowsPowerShellScript.6992e768_20fa_4bc1_80fd_1b116ad8bc00.MT" Accessibility="Public" RunAs="Core!Microsoft.SystemCenter.ServiceManager.WorkflowAccount" Batching="false">
<Configuration>
<IncludeSchemaTypes>
<SchemaType>Windows!Microsoft.Windows.PowerShellSchema</SchemaType>
</IncludeSchemaTypes>
<xsd:element name="WebServiceEndPoint" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="SMARunbookName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="azureSettingsFile" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="imageName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="vmName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="instanceSize" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="adminUserName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="domain" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="domainUserName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="domainPassword" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="affinityGroup" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="networkName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="azureStorageAccountName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="subnetName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="adminPassword" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="azureAccountName" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="smManagementServer" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
<xsd:element name="activityID" type="xsd:string" xmlns:xsd="https://www.w3.org/2001/XMLSchema" />
</Configuration>
<OverrideableParameters>
<OverrideableParameter ID="WebServiceEndPoint" Selector="$Config/WebServiceEndPoint$" ParameterType="string" />
<OverrideableParameter ID="SMARunbookName" Selector="$Config/SMARunbookName$" ParameterType="string" />
<OverrideableParameter ID="azureSettingsFile" Selector="$Config/azureSettingsFile$" ParameterType="string" />
<OverrideableParameter ID="imageName" Selector="$Config/imageName$" ParameterType="string" />
<OverrideableParameter ID="vmName" Selector="$Config/vmName$" ParameterType="string" />
<OverrideableParameter ID="instanceSize" Selector="$Config/instanceSize$" ParameterType="string" />
<OverrideableParameter ID="adminUserName" Selector="$Config/adminUserName$" ParameterType="string" />
<OverrideableParameter ID="domain" Selector="$Config/domain$" ParameterType="string" />
<OverrideableParameter ID="domainUserName" Selector="$Config/domainUserName$" ParameterType="string" />
<OverrideableParameter ID="domainPassword" Selector="$Config/domainPassword$" ParameterType="string" />
<OverrideableParameter ID="affinityGroup" Selector="$Config/affinityGroup$" ParameterType="string" />
<OverrideableParameter ID="networkName" Selector="$Config/networkName$" ParameterType="string" />
<OverrideableParameter ID="azureStorageAccountName" Selector="$Config/azureStorageAccountName$" ParameterType="string" />
<OverrideableParameter ID="subnetName" Selector="$Config/subnetName$" ParameterType="string" />
<OverrideableParameter ID="adminPassword" Selector="$Config/adminPassword$" ParameterType="string" />
<OverrideableParameter ID="azureAccountName" Selector="$Config/azureAccountName$" ParameterType="string" />
<OverrideableParameter ID="smManagementServer" Selector="$Config/smManagementServer$" ParameterType="string" />
<OverrideableParameter ID="activityID" Selector="$Config/activityID$" ParameterType="string" />
</OverrideableParameters>
<ModuleImplementation Isolation="Any">
<Composite>
<MemberModules>
<WriteAction ID="DeployVM.WindowsPowerShellScript.6992e768_20fa_4bc1_80fd_1b116ad8bc00.PSWA" TypeID="Windows!Microsoft.Windows.PowerShellWriteAction">
<ScriptName>DoWork.ps1</ScriptName>
<ScriptBody>param ( [string]$WebServiceEndPoint,[string]$SMARunbookName,[string]$azureSettingsFile,[string]$imageName,[string]$vmName,[string]$instanceSize,[string]$adminUserName,[string]$domain,[string]$domainUserName,[string]$domainPassword,[string]$affinityGroup,[string]$networkName,[string]$azureStorageAccountName,[string]$subnetName,[string]$adminPassword,[string]$azureAccountName,[string]$smManagementServer,[string]$activityID )
Start-SmaRunbook -WebServiceEndpoint $WebServiceEndpoint -Name $SMARunbookName -Parameters @{"azureSettingsFile" = "$azureSettingsFile"; "azureAccountName" = "$azureAccountName"; "imageName" = "$imageName"; "vmName" = "$vmName"; "instanceSize" = "$instanceSize"; "adminUserName" = "$adminUserName"; "adminPassword" = "$adminPassword"; "domain" = "$domain"; "domainUserName" = "$domainUserName"; "domainPassword" = "$domainPassword"; "affinityGroup" = "$affinityGroup"; "networkName" = "$networkName"; "azureStorageAccountName" = "$azureStorageAccountName"; "subnetName" = "$subnetName"; "smManagementServer" = "$smManagementServer"; "activityID" = "$activityID"}</ScriptBody>
<SnapIns />
<Parameters>
<Parameter>
<Name>WebServiceEndPoint</Name>
<Value>$Config/WebServiceEndPoint$</Value>
</Parameter>
<Parameter>
<Name>SMARunbookName</Name>
<Value>$Config/SMARunbookName$</Value>
</Parameter>
<Parameter>
<Name>azureSettingsFile</Name>
<Value>$Config/azureSettingsFile$</Value>
</Parameter>
<Parameter>
<Name>imageName</Name>
<Value>$Config/imageName$</Value>
</Parameter>
<Parameter>
<Name>vmName</Name>
<Value>$Config/vmName$</Value>
</Parameter>
<Parameter>
<Name>instanceSize</Name>
<Value>$Config/instanceSize$</Value>
</Parameter>
<Parameter>
<Name>adminUserName</Name>
<Value>$Config/adminUserName$</Value>
</Parameter>
<Parameter>
<Name>domain</Name>
<Value>$Config/domain$</Value>
</Parameter>
<Parameter>
<Name>domainUserName</Name>
<Value>$Config/domainUserName$</Value>
</Parameter>
<Parameter>
<Name>domainPassword</Name>
<Value>$Config/domainPassword$</Value>
</Parameter>
<Parameter>
<Name>affinityGroup</Name>
<Value>$Config/affinityGroup$</Value>
</Parameter>
<Parameter>
<Name>networkName</Name>
<Value>$Config/networkName$</Value>
</Parameter>
<Parameter>
<Name>azureStorageAccountName</Name>
<Value>$Config/azureStorageAccountName$</Value>
</Parameter>
<Parameter>
<Name>subnetName</Name>
<Value>$Config/subnetName$</Value>
</Parameter>
<Parameter>
<Name>adminPassword</Name>
<Value>$Config/adminPassword$</Value>
</Parameter>
<Parameter>
<Name>azureAccountName</Name>
<Value>$Config/azureAccountName$</Value>
</Parameter>
<Parameter>
<Name>smManagementServer</Name>
<Value>$Config/smManagementServer$</Value>
</Parameter>
<Parameter>
<Name>activityID</Name>
<Value>$Config/activityID$</Value>
</Parameter>
</Parameters>
<TimeoutSeconds>300</TimeoutSeconds>
<StrictErrorHandling>true</StrictErrorHandling>
<SerializationDepth>3</SerializationDepth>
</WriteAction>
</MemberModules>
<Composition>
<Node ID="DeployVM.WindowsPowerShellScript.6992e768_20fa_4bc1_80fd_1b116ad8bc00.PSWA" />
</Composition>
</Composite>
</ModuleImplementation>
<InputType>System!System.BaseData</InputType>
</WriteActionModuleType>
</ModuleTypes>
</TypeDefinitions>
<Categories>
<Category ID="Custom.Example.Azure.Category" Value="Console!Microsoft.EnterpriseManagement.ServiceManager.ManagementPack">
<ManagementPackName>Custom.Example.Azure</ManagementPackName>
<ManagementPackVersion>1.0.0.0</ManagementPackVersion>
</Category>
<Category ID="DeployVMCategory" Target="DeployVM" Value="EnterpriseManagement!Microsoft.EnterpriseManagement.ServiceManager.Rules.WorkflowSubscriptions" />
</Categories>
<Monitoring>
<Rules>
<Rule ID="DeployVM" Enabled="true" Target="SystemCenter!Microsoft.SystemCenter.SubscriptionWorkflowTarget" ConfirmDelivery="true" Remotable="true" Priority="Normal" DiscardLevel="100">
<Category>Notification</Category>
<DataSources>
<DataSource ID="DS" TypeID="SystemCenter1!Microsoft.SystemCenter.CmdbInstanceSubscription.DataSourceModule">
<Subscription>
<InstanceSubscription Type="$MPElement[Name='Custom.Example.Azure.DeployVM']$">
<UpdateInstance>
<Criteria>
<Expression>
<SimpleExpression>
<ValueExpression>
<Property State="Post">$Context/Property[Type='Alias_952b56e8_dd9f_480c_8f57_1d53f5894aca!System.WorkItem.Activity']/Status$</Property>
</ValueExpression>
<Operator>Equal</Operator>
<ValueExpression>
<Value>{11fc3cef-15e5-bca4-dee0-9c1155ec8d83}</Value>
</ValueExpression>
</SimpleExpression>
</Expression>
</Criteria>
</UpdateInstance>
</InstanceSubscription>
<PollingIntervalInSeconds>60</PollingIntervalInSeconds>
<BatchSize>100</BatchSize>
</Subscription>
</DataSource>
</DataSources>
<WriteActions>
<WriteAction ID="WA" TypeID="SystemCenter1!Microsoft.EnterpriseManagement.SystemCenter.Subscription.WindowsWorkflowTaskWriteAction">
<Subscription>
<WindowsWorkflowConfiguration>
<AssemblyName>DeployVM</AssemblyName>
<WorkflowTypeName>WorkflowAuthoring.DeployVM</WorkflowTypeName>
<WorkflowParameters>
<WorkflowParameter Name="windowsPowerShellScript1_WebServiceEndPoint" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/WebServiceEndpoint$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_azureSettingsFile" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/azureSettingsFile$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_imageName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/imageName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_vmName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/vmName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_instanceSize" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/instanceSize$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_adminUserName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/adminUserName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_domain" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/domain$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_domainUserName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/domainUserName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_domainPassword" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/domainPassword$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_affinityGroup" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/affinityGroup$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_networkName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/networkName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_azureStorageAccountName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/azureStorageAccountName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_subnetName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/subnetName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_SMARunbookName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/SMARunbookName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_adminPassword" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/adminPassword$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_azureAccountName" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/azureAccountName$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_smManagementServer" Type="string">$Data/Property[@ID='$MPElement[Name="Custom.Example.Azure.DeployVM"]/smManagementServer$' and @State='Post']$</WorkflowParameter>
<WorkflowParameter Name="windowsPowerShellScript1_activityID" Type="string">$Data/Property[@ID='$MPElement[Name="System_WorkItem_Library!System.WorkItem"]/Id$' and @State='Post']$</WorkflowParameter>
</WorkflowParameters>
<RetryExceptions />
<RetryDelaySeconds>60</RetryDelaySeconds>
<MaximumRunningTimeSeconds>300</MaximumRunningTimeSeconds>
</WindowsWorkflowConfiguration>
</Subscription>
</WriteAction>
</WriteActions>
</Rule>
</Rules>
<Tasks>
<Task ID="DeployVM.WindowsPowerShellScript.6992e768_20fa_4bc1_80fd_1b116ad8bc00" Accessibility="Public" Enabled="true" Target="Windows!Microsoft.Windows.Computer" Timeout="300" Remotable="true">
<Category>Notification</Category>
<WriteAction ID="DeployVM.WindowsPowerShellScript.6992e768_20fa_4bc1_80fd_1b116ad8bc00.WA" TypeID="DeployVM.WindowsPowerShellScript.6992e768_20fa_4bc1_80fd_1b116ad8bc00.MT">
<WebServiceEndPoint />
<SMARunbookName />
<azureSettingsFile />
<imageName />
<vmName />
<instanceSize />
<adminUserName />
<domain />
<domainUserName />
<domainPassword />
<affinityGroup />
<networkName />
<azureStorageAccountName />
<subnetName />
<adminPassword />
<azureAccountName />
<smManagementServer />
<activityID />
</WriteAction>
</Task>
</Tasks>
</Monitoring>
<Templates>
<ObjectTemplate ID="Template.87826befabdb478da4e836bdb4b93c8e" TypeID="Custom.Example.Azure.DeployVM">
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/WebServiceEndpoint$">https://mysmaserver.contoso.com</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/azureSettingsFile$">c:\temp\myAzureSettings.publishsettings</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/imageName$">w2012r2base3</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/vmName$">rslatenTest</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/instanceSize$">A0</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/adminUserName$">rslaten</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/adminPassword$">P@$$W0Rd1</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/domain$">contoso.com</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/domainUserName$">rslaten</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/domainPassword$">P@$$W0Rd1</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/affinityGroup$">Lab</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/networkName$">Lab</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/azureStorageAccountName$">rslaten</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/subnetName$">Subnet-1</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/SMARunbookName$">DeployVMInAzure</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/azureAccountName$">myAzureAccount@myemailaccount.com</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/smManagementServer$">sm1.contoso.com</Property>
<Property Path="$Context/Property[Type='Alias_952b56e8_dd9f_480c_8f57_1d53f5894aca!System.WorkItem.Activity']/Skip$">False</Property>
<Property Path="$Context/Property[Type='System_WorkItem_Library!System.WorkItem']/Title$">Deploy Azure VM</Property>
<Property Path="$Context/Property[Type='System!System.Entity']/DisplayName$">Deploy Azure VM</Property>
</ObjectTemplate>
<ObjectTemplate ID="Template.e0b9b5533a9d4a82b37658e95c03f0f7" TypeID="Example!CustomForm_0c972943_1f64_4cd2_84bc_6a9c7da0c6eb_TypeProjection">
<Object Path="$Context/Path[Relationship='Alias_952b56e8_dd9f_480c_8f57_1d53f5894aca!System.WorkItemContainsActivity' TypeConstraint='Custom.Example.Azure.DeployVM']$">
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/WebServiceEndpoint$">https://mysmaserver.contoso.com</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/azureSettingsFile$">c:\temp\myAzureSettings.publishsettings</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/imageName$">w2012r2base3</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/vmName$">rslatenTest</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/instanceSize$">A0</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/adminUserName$">rslaten</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/adminPassword$">P@$$W0Rd1</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/domain$">contoso.com</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/domainUserName$">rslaten</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/domainPassword$">P@$$W0Rd1</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/affinityGroup$">Lab</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/networkName$">Lab</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/azureStorageAccountName$">rslaten</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/subnetName$">Subnet-1</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/SMARunbookName$">DeployVMInAzure</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/azureAccountName$">myAzureAccount@myemailaccount.com</Property>
<Property Path="$Context/Property[Type='Custom.Example.Azure.DeployVM']/smManagementServer$">sm1.contoso.com</Property>
<Property Path="$Context/Property[Type='Alias_952b56e8_dd9f_480c_8f57_1d53f5894aca!System.WorkItem.Activity']/SequenceId$">0</Property>
<Property Path="$Context/Property[Type='Alias_952b56e8_dd9f_480c_8f57_1d53f5894aca!System.WorkItem.Activity']/ChildId$">828</Property>
<Property Path="$Context/Property[Type='Alias_952b56e8_dd9f_480c_8f57_1d53f5894aca!System.WorkItem.Activity']/Skip$">False</Property>
<Property Path="$Context/Property[Type='System_WorkItem_Library!System.WorkItem']/Title$">Deploy Azure VM</Property>
<Property Path="$Context/Property[Type='System!System.Entity']/DisplayName$">Deploy Azure VM</Property>
</Object>
</ObjectTemplate>
</Templates>
<LanguagePacks>
<LanguagePack ID="ENU" IsDefault="true">
<DisplayStrings>
<DisplayString ElementID="Custom.Example.Azure">
<Name>Custom.Example.Azure</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM">
<Name>Custom.Example.Azure.DeployVM</Name>
<Description>Specify your class description.</Description>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="WebServiceEndpoint">
<Name>WebServiceEndpoint</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="SMARunbookName">
<Name>SMARunbookName</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="azureSettingsFile">
<Name>azureSettingsFile</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="imageName">
<Name>imageName</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="vmName">
<Name>vmName</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="instanceSize">
<Name>instanceSize</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="adminUserName">
<Name>adminUserName</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="adminPassword">
<Name>adminPassword</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="domain">
<Name>domain</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="domainUserName">
<Name>domainUserName</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="domainPassword">
<Name>domainPassword</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="affinityGroup">
<Name>affinityGroup</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="networkName">
<Name>networkName</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="azureStorageAccountName">
<Name>azureStorageAccountName</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="subnetName">
<Name>subnetName</Name>
</DisplayString>
<DisplayString ElementID="DeployVM">
<Name>DeployVM</Name>
</DisplayString>
<DisplayString ElementID="DeployVM.WindowsPowerShellScript.6992e768_20fa_4bc1_80fd_1b116ad8bc00">
<Name>DeployVM.WindowsPowerShellScript.6992e768_20fa_4bc1_80fd_1b116ad8bc00</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="azureAccountName">
<Name>azureAccountName</Name>
</DisplayString>
<DisplayString ElementID="Custom.Example.Azure.DeployVM" SubElementID="smManagementServer">
<Name>smManagementServer</Name>
</DisplayString>
<DisplayString ElementID="Template.87826befabdb478da4e836bdb4b93c8e">
<Name>Deploy Azure VM Template</Name>
</DisplayString>
<DisplayString ElementID="Template.e0b9b5533a9d4a82b37658e95c03f0f7">
<Name>Deploy Azure VM Service Request Template</Name>
</DisplayString>
</DisplayStrings>
</LanguagePack>
</LanguagePacks>
<Extensions>
<RequestOffering ID="Offering59cfa70b0f134665821820b78a3f744a" InstanceName="Deploy Azure Virtual Machine" Title="Deploy Azure Virtual Machine" PublishDate="2014-08-23T16:45:46-05:00" Status="System.Offering.StatusEnum.Published" TargetTemplate="Template.e0b9b5533a9d4a82b37658e95c03f0f7" HideGotoRequestButton="false">
<PresentationMappingTemplate>
<Sources>
<Source Id="00000000-0000-0000-0000-000000000000" Ordinal="0" ReadOnly="false" Optional="false" ControlType="System.SupportingItem.PortalControl">
<ControlConfiguration>
<Dependencies />
<AddressableOutputs>
<AddressableOutput OutputName="Token: Portal User Name" OutputType="string" />
</AddressableOutputs>
</ControlConfiguration>
<Targets />
</Source>
<Source Id="979c2819-ad73-4319-b5c7-e8b55edc956b" Ordinal="1" Prompt="Instance Size" ReadOnly="false" Optional="false" ControlType="System.SupportingItem.PortalControl.InlineList">
<ControlConfiguration>
<Dependencies />
<AddressableOutputs>
<AddressableOutput OutputName="ListValue" OutputType="string" />
</AddressableOutputs>
<Configuration>
<Details>
<ListValue DisplayName="A0" IsDefault="true" />
<ListValue DisplayName="A1" IsDefault="false" />
<ListValue DisplayName="A2" IsDefault="false" />
<ListValue DisplayName="A3" IsDefault="false" />
<ListValue DisplayName="A4" IsDefault="false" />
<ListValue DisplayName="A5" IsDefault="false" />
<ListValue DisplayName="A6" IsDefault="false" />
<ListValue DisplayName="A7" IsDefault="false" />
<ListValue DisplayName="A8" IsDefault="false" />
<ListValue DisplayName="A9" IsDefault="false" />
</Details>
</Configuration>
</ControlConfiguration>
<Targets>
<Target Path="$Target/Path[Relationship='Activity!System.WorkItemContainsActivity']$?ChildId='828'/instanceSize" OutputName="ListValue" />
</Targets>
</Source>
</Sources>
</PresentationMappingTemplate>
</RequestOffering>
<ServiceOffering ID="Offeringa5d733744b234dfcb6d41383780ca6a4" InstanceName="Cloud Offerings" Title="Cloud Offerings" PublishDate="2014-08-23T16:46:55-05:00" Status="System.Offering.StatusEnum.Published" Category="System.ServiceOffering.CategoryEnum.General" CultureName="" />
</Extensions>
</ManagementPack>
Test the Solution
- Open the Service Manager Self-Service Portal
- Click on Cloud Offerings, click on Deploy Azure Virtual Machine, and click on Go to request form
- Select the appropriate instance size, click Next, and Submit. Once completed the request should also change to Completed.
- View the completed Runbook in the WAP Portal
- View the new VM in the Azure Portal