Proposed Pull Request Change

title description ms.topic ms.date ms.service ms.subservice ms.author ms.reviewer author ms.custom
Terraform based SCVMM VM management This article describes how to programmatically perform lifecycle operations on the SCVMM managed on-premises virtual machines using the Terraform templates. how-to 02/09/2026 azure-arc azure-arc-scvmm v-gajeronika v-gajeronika Jeronika-MS ['build-2025']
📄 Document Links
GitHub View on GitHub Microsoft Learn View on Microsoft Learn
Content Truncation Detected
The generated rewrite appears to be incomplete.
Original lines: -
Output lines: -
Ratio: -
Raw New Markdown
Generating updated version of doc...
Rendered New Markdown
Generating updated version of doc...
+0 -0
+0 -0
--- title: Terraform based SCVMM VM management description: This article describes how to programmatically perform lifecycle operations on the SCVMM managed on-premises virtual machines using the Terraform templates. ms.topic: how-to ms.date: 02/09/2026 ms.service: azure-arc ms.subservice: azure-arc-scvmm ms.author: v-gajeronika ms.reviewer: v-gajeronika author: Jeronika-MS ms.custom: - build-2025 # Customer intent: "As a cloud infrastructure engineer, I want to manage SCVMM on-premises virtual machines using Terraform, so that I can automate lifecycle operations and enhance efficiency in resource management." --- # Terraform based SCVMM VM management This article describes how to programmatically perform lifecycle operations on the SCVMM managed on-premises virtual machines by using the Terraform templates. [Hashicorp Terraform](https://www.terraform.io/) is an open-source IaC (Infrastructure-as-Code) tool to configure and deploy cloud infrastructure. Terraform enables the management of your SCVMM based virtual infrastructure by using AzAPI Terraform providers. You can access the complete set of Terraform templates available with Azure Arc enabled SCVMM [here](/azure/templates/microsoft.scvmm/virtualmachineinstances?pivots=deployment-language-terraform). This article covers the following scenarios: - Create a new SCVMM-managed on-premises Virtual Machine from Azure - Enable a SCVMM-managed on-premises Virtual Machine for management in Azure - Remove the Azure based management capability for a SCVMM-managed on-premises Virtual Machine ## Best practices - **Use version control**: Keep your Terraform configuration files under version control (for example, Git) to track changes over time. - **State management**: Regularly back up your Terraform state files to avoid data loss. # [Scenario 1: Create a VM](#tab/scenario1) ### Prerequisites Make sure you have the following prerequisites before you create a new virtual machine: - An Azure subscription and resource group where you have the Arc SCVMM VM Contributor role or a custom RBAC role with the required permissions to perform lifecycle operations on a Virtual Machine. - An Arc-enabled SCVMM server with the Azure Arc resource bridge in a Running state. - A workstation machine with Terraform installed. - An Azure-enabled cloud resource on which you have Arc SCVMM Private Cloud Resource User role. - An Azure-enabled virtual machine template resource on which you have Arc SCVMM Private Cloud Resource User role. - An Azure-enabled virtual network resource on which you have Arc SCVMM Private Cloud Resource User role. ### Step 1: Define the VM variables in a *variables.tf* file Here's a sample `variables.tf` file with placeholders. ```terraform variable "subscription_id" { description = "The subscription ID for the Azure account." type = string } variable "resource_group_name" { description = "The name of the resource group." type = string } variable "location" { description = "The location/region where the resources will be created." type = string } variable "machine_name" { description = "The name of the machine." type = string } variable "inventory_item_id" { description = "The ID of the Inventory Item for the VM." type = string } variable "vm_username" { description = "The admin username for the VM." type = string } variable "vm_password" { description = "The admin password for the VM." type = string } variable "cloud_id" { description = "The ID of the cloud." type = string } variable "template_id" { description = "The ID of the template." type = string } variable "virtual_network_id" { description = "The ID of the virtual network." type = string } variable "availability_set_name" { description = "The name of the availability set." type = string } variable "vmmserver_id" { description = "The ID of the SCVMM server." type = string } variable "custom_location_id" { description = "The ID of the custom location." type = string } ``` ### Step 2: Define the metadata and credentials in a *tfvars* file Here's a sample `createscvmmVM.tfvars` file with placeholders. ```terraform subscription_id = "your-subscription-id" resource_group_name = "your-resource-group" location = "eastus" machine_name = "vm-name" vm_username = "Administrator" vm_password = "your_vm_password" vmmserver_id = "/subscriptions/your-subscription-id/resourceGroups/your-resource-group/providers/Microsoft.SCVMM/vmmServers/your-vmmserver-name" availability_set_name = "/subscriptions/your-subscription-id/resourceGroups/your-resource-group/providers/Microsoft.SCVMM/AvailabilitySets/your-availabilityset-name" #this parameter is optional cloud_id = "/subscriptions/your-subscription-id/resourceGroups/your-resource-group/providers/Microsoft.SCVMM/Clouds/your-vmmcloud-name" template_id = "/subscriptions/your-subscription-id/resourceGroups/your-resource-group/providers/Microsoft.SCVMM/VirtualMachineTemplates/your-template-name" virtual_network_id = "/subscriptions/your-subscription-id/resourceGroups/your-resource-group/providers/Microsoft.SCVMM/VirtualNetworks/your-vmnetwork-name" custom_location_id = "/subscriptions/your-subscription-id/resourcegroups/your-resource-group/providers/Microsoft.extendedlocation/customlocations/your-customlocation-name" ``` ### Step 3: Define the VM configuration in a *main.tf* file Here's a sample `main.tf` file with placeholders. ```terraform terraform { required_providers { azurerm = { source = "hashicorp/azurerm" version = ">= 3.0" } azapi = { source = "azure/azapi" version = ">= 1.0.0" } } } # Configure the AzureRM provider with the subscription ID provider "azurerm" { features {} subscription_id = var.subscription_id } # Configure the AzAPI provider with the subscription ID provider "azapi" { subscription_id = var.subscription_id } # Retrieve the resource group details data "azurerm_resource_group" "example" { name = var.resource_group_name } # Create a Hybrid machine resource in Azure resource "azapi_resource" "test_machine02" { schema_validation_enabled = false parent_id = data.azurerm_resource_group.example.id type = "Microsoft.HybridCompute/machines@2024-07-10" name = var.machine_name location = var.location body = { kind = "SCVMM" identity = { type = "SystemAssigned" } } } # Create a Virtual Machine instance using the Hybrid machine and Inventory Item ID resource "azapi_resource" "test_inventory_vm001" { schema_validation_enabled = false type = "Microsoft.SCVMM/VirtualMachineInstances@2024-06-01" name = "default" parent_id = azapi_resource.test_machine01.id body = { properties = { infrastructureProfile = { templateId = var.template_id cloudId = var.cloud_id vmName = var.machine_name } # Availability sets, OS profile and hardware profile are optional availabilitySets = [ { name = var.availability_set_name } ] # Override VM template to customize VM creation osProfile = { computerName = "myVM" adminPassword = var.vm_password domainName = "cdmlab" domainUsername = "cdmlabuser" domainPassword = "your_domain_password" workgroup = "myWorkgroup" runOnceCommands = "echo Hello; echo World" } hardwareProfile = { cpuCount = 4 memoryMB = 3072 limitCpuForMigration = "true" } networkProfile = { networkInterfaces = [ { name = "nic1" macAddress = "00:0A:95:9D:68:16" virtualNetworkId = var.virtual_network_id ipv4AddressType = "Dynamic" } ] } storageProfile = { disks = [ { name = "disk1" diskId = "disk-unique-id-1" diskSizeGB = 30 bus = 0 lun = 0 busType = "SCSI" vhdType = "Dynamic" } ] } } extendedLocation = { type = "CustomLocation" name = var.custom_location_id } } depends_on = [azapi_resource.test_machine01] } # Install Arc agent on the VM resource "azapi_resource" "guestAgent" { type = "Microsoft.SCVMM/virtualMachineInstances/guestAgents@2024-06-01" parent_id = azapi_resource.test_inventory_vm001.id name = "default" body = { properties = { credentials = { username = var.vm_username password = var.vm_password } provisioningAction = "install" } } schema_validation_enabled = false ignore_missing_property = false depends_on = [azapi_resource.test_inventory_vm001] } ``` ### Step 4: Run Terraform commands Use the -var-file flag to pass the *.tfvars* file during Terraform commands. - Initialize Terraform (if not already initialized): `terraform init` - Validate the configuration: `terraform validate -var-file="createscvmmVM.tfvars"` - Plan the changes: `terraform plan -var-file="createscvmmVM.tfvars"` - Apply the changes: `terraform apply -var-file="createscvmmVM.tfvars"` Enter yes to confirm the prompt and apply the changes. # [Scenario 2: Enable a VM for Azure management](#tab/scenario2) ### Prerequisites Make sure you have the following prerequisites before you create a new virtual machine: - An Azure subscription and resource group where you have the Arc SCVMM VM Contributor role or a custom RBAC role with the required permissions to perform lifecycle operations on a Virtual Machine. - An Arc-enabled SCVMM server with the Azure Arc resource bridge in a Running state. - A workstation machine with Terraform installed. ### Step 1: Define the VM variables in a *variables.tf* file Here's a sample `variables.tf` file with placeholders. ```terraform variable "subscription_id" { description = "The subscription ID for the Azure account." type = string } variable "resource_group_name" { description = "The name of the resource group." type = string } variable "location" { description = "The location/region where the resources will be created." type = string } variable "machine_name" { description = "The name of the machine." type = string } variable "inventory_item_id" { description = "The ID of the Inventory Item for the VM." type = string } variable "vm_username" { description = "The admin username for the VM." type = string } variable "vm_password" { description = "The admin password for the VM." type = string } variable "vmmserver_id" { description = "The ID of the SCVMM server." type = string } variable "custom_location_id" { description = "The ID of the custom location." type = string } ``` ### Step 2: Define the metadata and credentials in a *tfvars* file Here's a sample `createscvmmVM.tfvars` file with placeholders. ```terraform subscription_id = "your-subscription-id" resource_group_name = "your-resource-group" location = "eastus" machine_name = "vm-name" vm_username = "Administrator" vm_password = "your_vm_password" inventory_item_id = "/subscriptions/your-subscription-id/resourceGroups/your-resource-group/providers/Microsoft.ScVmm/vmmServers/arcscvmm-777-2-vmmserver/InventoryItems/b3b8c107-9a7a-4ac2-b0aa-010ba7caba64" vmmserver_id = "/subscriptions/your-subscription-id/resourceGroups/your-resource-group/providers/Microsoft.ScVmm/vmmServers/arcscvmm-777-2-vmmserver" custom_location_id = "/subscriptions/your-subscription-id/resourcegroups/your-resource-group/providers/microsoft.extendedlocation/customlocations/arcscvmm-777-2-cl" ``` >[!NOTE] >`vm_username` and `vm_password` are optional parameters. You need them only to install the Azure Arc agent on the VM. ### Step 3: Define the VM configuration in a *main.tf* file Here's a sample `main.tf` file with placeholders. ```terraform terraform { required_providers { azurerm = { source = "hashicorp/azurerm" version = ">= 3.0" } azapi = { source = "azure/azapi" version = ">= 1.0.0" } } } # Configure the AzureRM provider with the subscription ID provider "azurerm" { features {} subscription_id = var.subscription_id } # Configure the AzAPI provider with the subscription ID provider "azapi" { subscription_id = var.subscription_id } # Retrieve the resource group details data "azurerm_resource_group" "example" { name = var.resource_group_name } # Create a Hybrid Machine resource in Azure resource "azapi_resource" "vm-name" { schema_validation_enabled = false parent_id = data.azurerm_resource_group.example.id type = "Microsoft.HybridCompute/machines@2024-07-10" name = var.machine_name location = var.location body = { kind = "SCVMM" identity = { type = "SystemAssigned" } } } # Enable a Virtual Machine instance using the Hybrid machine and Inventory Item ID resource "azapi_resource" "test_inventory_vm" { schema_validation_enabled = false type = "Microsoft.SCVMM/VirtualMachineInstances@2024-06-01" name = "default" parent_id = azapi_resource.vm-name.id body = { properties = { infrastructureProfile = { inventoryItemId = var.inventory_item_id vmmServerId = var.vmmserver_id } } extendedLocation = { type = "CustomLocation" name = var.custom_location_id } } depends_on = [azapi_resource.vm-name] } # Install Arc agent on the VM (optional step) resource "azapi_resource" "guestAgent" { type = "Microsoft.SCVMM/virtualMachineInstances/guestAgents@2024-06-01" parent_id = azapi_resource.test_inventory_vm.id name = "default" body = { properties = { credentials = { username = var.vm_username password = var.vm_password } provisioningAction = "install" } } schema_validation_enabled = false ignore_missing_property = false depends_on = [azapi_resource.test_inventory_vm] } ``` ### Step 4: Run Terraform commands Use the `-var-file` flag to pass the *.tfvars* file during Terraform commands. - Initialize Terraform (if not already initialized): `terraform init` - Validate the configuration: `terraform validate -var-file="enablescvmmVM.tfvars"` - Plan the changes: `terraform plan -var-file="enablescvmmVM.tfvars"` - Apply the changes: `terraform apply -var-file="enablescvmmVM.tfvars"` Enter yes to confirm the prompt and apply the changes. # [Scenario 3: Remove from Azure](#tab/scenario3) ### Prerequisites Make sure you have the following prerequisites before you create a new virtual machine: - An Azure subscription and resource group where you have the Arc SCVMM VM Contributor role or a custom RBAC role with the required permissions to perform lifecycle operations on a Virtual Machine. - An Arc-enabled SCVMM server with the Azure Arc resource bridge in a Running state. - A workstation machine with Terraform installed. - The virtual machine that you want to remove from Azure-based management is enabled for management in Azure and has an Azure resource. Consider the following points before you remove the VM from Azure: - This action removes the Azure Resource Manager representation of the machine. To manage the machine from Azure again, you need to enable the machine in Azure. Before you proceed, make sure that the VM doesn't break any dependencies and take backups of any important data, if needed. - To remove a SCVMM-managed VM from Azure-based management, remove the VM definition (or comment out) from your Terraform configuration and run: ```terraform terraform plan ``` Terraform shows that the VM is planned for removal from Azure because it no longer exists in the configuration. If you agree with the changes, run: ```terraform terraform apply ``` This command destroys the Azure representation of the VM if it’s no longer in the configuration. --- ## Next steps - [Perform operations on SCVMM VMs from Azure](/azure/azure-arc/system-center-virtual-machine-manager/perform-vm-ops-on-scvmm-through-azure). - Manage [Arc-enabled SCVMM VM extensions](/azure/azure-arc/servers/manage-vm-extensions).
Success! Branch created successfully. Create Pull Request on GitHub
Error: