terraform-provider-azurerm
terraform-provider-azurerm copied to clipboard
Issue with 'terraform plan -destroy' for resources created with count
Is there an existing issue for this?
- [X] I have searched the existing issues
Community Note
- Please vote on this issue by adding a :thumbsup: reaction to the original issue to help the community and maintainers prioritize this request
- Please do not leave "+1" or "me too" comments, they generate extra noise for issue followers and do not help prioritize the request
- If you are interested in working on this issue or have submitted a pull request, please leave a comment and review the contribution guide to help.
Issue with "terraform plan -destroy -target=<target_id_count[1]>" for count-based resources
Description
We're creating multiple resources using COUNT meta-arg, which reads configuration from JSON array and iterates over JSON objects, and keep on creating resources. We have three VMs (VM[0-2] with their RBAC Role (Contributor) on the resource group.
When we want to delete the VM[1] using command, it marks the RBAC assignment for VM[0] & VM[2] as well, which is not as per expectation
Terraform Version
2.99
AzureRM Provider Version
2.8
Affected Resource(s)/Data Source(s)
azurerm_role_assignment
Terraform Configuration Files
############ START: Terraform Configuration #################
variable "location" { default = "EastUS" }
terraform {
required_providers {
azurerm = {
source = "hashicorp/azurerm"
version = "~>3.0"
}
}
}
# This SP details should NEVER be part of tfvars or tf file, instead it should be supplied via env variables.
provider "azurerm" {
features {}
subscription_id = "<subs-id>"
tenant_id = "<tenant-id>"
client_id = "<service-principal-id>
client_secret = "<secret>"
}
locals {
env_data = jsondecode(file("env_config.json"))["target_vms"]
## Specifies how many wcsccm instances we should be creating
instance_count = length(local.env_data)
}
resource "azurerm_resource_group" "rg" {
name = "wcsccm-poc-rg"
location = "East US"
tags = {
Name = "POC-COUNT"
}
}
resource "azurerm_virtual_network" "vnet" {
name = "poc-vnet"
location = var.location
resource_group_name = azurerm_resource_group.rg.name
address_space = ["10.207.229.0/24"]
tags = {
Name = "POC-COUNT"
}
}
resource "azurerm_subnet" "subnet" {
name = "poc-vnet-subnet"
resource_group_name = azurerm_resource_group.rg.name
virtual_network_name = azurerm_virtual_network.vnet.name
address_prefixes = ["10.207.229.0/28"]
}
resource "azurerm_network_interface" "nic" {
count = local.instance_count
name = "nic-${count.index}"
location = azurerm_resource_group.rg.location
resource_group_name = azurerm_resource_group.rg.name
ip_configuration {
name = "ip-${count.index}"
subnet_id = azurerm_subnet.subnet.id
private_ip_address_allocation = "Dynamic"
}
}
resource "azurerm_linux_virtual_machine" "vm" {
count = local.instance_count
name = local.env_data[count.index].name
location = azurerm_resource_group.rg.location
resource_group_name = azurerm_resource_group.rg.name
network_interface_ids = [azurerm_network_interface.nic[count.index].id]
size = "Standard_D2ds_v5"
computer_name = local.env_data[count.index].name
admin_username = "myazureuser"
# license_type = "RHEL_BYOS"
os_disk {
name = "vm-osdisk-${count.index}"
caching = "ReadWrite"
storage_account_type = "Premium_LRS"
disk_size_gb = 128
}
source_image_reference {
publisher = "canonical"
offer = "0001-com-ubuntu-minimal-jammy"
sku = "minimal-22_04-lts-gen2"
version = "latest"
}
identity {
type = "SystemAssigned"
}
admin_ssh_key {
public_key = "ssh-rsa AAAAB3NzaC1yc2EAAAABJQAAAQB29Q4Mo+8ueEmCy5enTsch5RR1L5fIM6SFmX21riiGVN0MsiNoUFf5nTeel7J6EbzZJipQy7GfIL0oiMPo/HxkLxLtVw1vB/ZNDo++3Fh3upZP9CWe5YJXdN90kIrGUArLMF3LrZc+iAHzByinpOxLIhUkuzJjTTBpSWvwTRr5XBVyq+cXmSdIab67SrbOoUaeffkR4C6XrEBjl0uJpfPdXfX5kq8wdwUTYs7JiuuachXthX9jtOOx0u98ZSUQbGgsTf4rM6NUEEfhy8Nxiuz3vsnU8z5Ff77sVCBfMhu/Zx9FAm7neiS2qPycxtEblEEZ8e/6D0FOZyQlAyQT+QVN rsa-key-20190305 mycloud admin common key"
username = "myazureuser"
}
tags = {
Name = "POC-COUNT"
}
}
resource "azurerm_role_assignment" "iam_role" {
count = local.instance_count
scope = azurerm_resource_group.rg.id
role_definition_name = "Contributor"
principal_id = azurerm_linux_virtual_machine.vm[count.index].identity[0].principal_id
}
#------------ OUTPUTS ----------------#
output "vm_output" {
description = "VM Details"
value = { for k, v in azurerm_linux_virtual_machine.vm : k => v.id }
}
output "iam_roles_output" {
description = "IAM Role details"
value = { for k, v in azurerm_role_assignment.iam_role : k => v.id }
}
############ END: Terraform Configuration #################
############ START: env_config.json #################
{
"target_vms": [
{
"name": "count-poc-vm1"
},
{
"name": "count-poc-vm2"
},
{
"name": "count-poc-vm3"
}
]
}
############ END: env_config.json #################
Debug Output/Panic Output
#[root@vm:4 wcsccm_temp](git:wcsccm_refactor) # terraform plan -destroy -target=azurerm_linux_virtual_machine.vm[1]
azurerm_resource_group.rg: Refreshing state... [id=/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg]
azurerm_virtual_network.vnet: Refreshing state... [id=/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Network/virtualNetworks/poc-vnet]
azurerm_subnet.subnet: Refreshing state... [id=/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Network/virtualNetworks/poc-vnet/subnets/poc-vnet-subnet]
azurerm_network_interface.nic[0]: Refreshing state... [id=/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Network/networkInterfaces/nic-0]
azurerm_network_interface.nic[2]: Refreshing state... [id=/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Network/networkInterfaces/nic-2]
azurerm_network_interface.nic[1]: Refreshing state... [id=/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Network/networkInterfaces/nic-1]
azurerm_linux_virtual_machine.vm[1]: Refreshing state... [id=/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Compute/virtualMachines/count-poc-vm2]
Terraform used the selected providers to generate the following execution plan. Resource actions are indicated with the following symbols:
- destroy
Terraform will perform the following actions:
# azurerm_linux_virtual_machine.vm[1] will be destroyed
- resource "azurerm_linux_virtual_machine" "vm" {
- admin_username = "myazureuser" -> null
- allow_extension_operations = true -> null
- bypass_platform_safety_checks_on_user_schedule_enabled = false -> null
- computer_name = "count-poc-vm2" -> null
- disable_password_authentication = true -> null
- disk_controller_type = "SCSI" -> null
- encryption_at_host_enabled = false -> null
- extensions_time_budget = "PT1H30M" -> null
- id = "/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Compute/virtualMachines/count-poc-vm2" -> null
- location = "eastus" -> null
- max_bid_price = -1 -> null
- name = "count-poc-vm2" -> null
- network_interface_ids = [
- "/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Network/networkInterfaces/nic-1",
] -> null
- patch_assessment_mode = "ImageDefault" -> null
- patch_mode = "ImageDefault" -> null
- platform_fault_domain = -1 -> null
- priority = "Regular" -> null
- private_ip_address = "10.207.229.6" -> null
- private_ip_addresses = [
- "10.207.229.6",
] -> null
- provision_vm_agent = true -> null
- public_ip_addresses = [] -> null
- resource_group_name = "wcsccm-poc-rg" -> null
- secure_boot_enabled = false -> null
- size = "Standard_D2ds_v5" -> null
- tags = {
- "Name" = "POC-COUNT"
} -> null
- virtual_machine_id = "61336656-1aca-4819-8cb2-0f89b3fcffe5" -> null
- vm_agent_platform_updates_enabled = false -> null
- vtpm_enabled = false -> null
- admin_ssh_key {
- public_key = "ssh-rsa AAAAB3NzaC1yc2EAAAABJQAAAQB29Q4Mo+8ueEmCy5enTsch5RR1L5fIM6SFmX21riiGVN0MsiNoUFf5nTeel7J6EbzZJipQy7GfIL0oiMPo/HxkLxLtVw1vB/ZNDo++3Fh3upZP9CWe5YJXdN90kIrGUArLMF3LrZc+iAHzByinpOxLIhUkuzJjTTBpSWvwTRr5XBVyq+cXmSdIab67SrbOoUaeffkR4C6XrEBjl0uJpfPdXfX5kq8wdwUTYs7JiuuachXthX9jtOOx0u98ZSUQbGgsTf4rM6NUEEfhy8Nxiuz3vsnU8z5Ff77sVCBfMhu/Zx9FAm7neiS2qPycxtEblEEZ8e/6D0FOZyQlAyQT+QVN rsa-key-20190305 mycloud admin common key" -> null
- username = "myazureuser" -> null
}
- identity {
- identity_ids = [] -> null
- principal_id = "e3c31b16-e430-4fb3-a187-cc41e5132d19" -> null
- tenant_id = "0fdcdd31-e3e2-49ba-b748-2c3def81bd6e" -> null
- type = "SystemAssigned" -> null
}
- os_disk {
- caching = "ReadWrite" -> null
- disk_size_gb = 128 -> null
- name = "vm-osdisk-1" -> null
- storage_account_type = "Premium_LRS" -> null
- write_accelerator_enabled = false -> null
}
- source_image_reference {
- offer = "0001-com-ubuntu-minimal-jammy" -> null
- publisher = "canonical" -> null
- sku = "minimal-22_04-lts-gen2" -> null
- version = "latest" -> null
}
}
# azurerm_role_assignment.iam_role[0] will be destroyed
- resource "azurerm_role_assignment" "iam_role" {
- id = "/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Authorization/roleAssignments/5444557e-c96c-d2fa-f90a-490a3005759b" -> null
- name = "5444557e-c96c-d2fa-f90a-490a3005759b" -> null
- principal_id = "7ffe82ea-abe8-4225-85c4-38e2229f5060" -> null
- principal_type = "ServicePrincipal" -> null
- role_definition_id = "/subscriptions/subscription_id_hidden/providers/Microsoft.Authorization/roleDefinitions/b24988ac-6180-42a0-ab88-20f7382dd24c" -> null
- role_definition_name = "Contributor" -> null
- scope = "/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg" -> null
}
# azurerm_role_assignment.iam_role[1] will be destroyed
- resource "azurerm_role_assignment" "iam_role" {
- id = "/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Authorization/roleAssignments/967e9c93-dbdd-edcf-b68f-32424d659d6f" -> null
- name = "967e9c93-dbdd-edcf-b68f-32424d659d6f" -> null
- principal_id = "e3c31b16-e430-4fb3-a187-cc41e5132d19" -> null
- principal_type = "ServicePrincipal" -> null
- role_definition_id = "/subscriptions/subscription_id_hidden/providers/Microsoft.Authorization/roleDefinitions/b24988ac-6180-42a0-ab88-20f7382dd24c" -> null
- role_definition_name = "Contributor" -> null
- scope = "/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg" -> null
}
# azurerm_role_assignment.iam_role[2] will be destroyed
- resource "azurerm_role_assignment" "iam_role" {
- id = "/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg/providers/Microsoft.Authorization/roleAssignments/cb9e712b-9c4c-6212-7367-b755fd558737" -> null
- name = "cb9e712b-9c4c-6212-7367-b755fd558737" -> null
- principal_id = "e7b34dc6-c213-4c41-9146-561cb842e4f4" -> null
- principal_type = "ServicePrincipal" -> null
- role_definition_id = "/subscriptions/subscription_id_hidden/providers/Microsoft.Authorization/roleDefinitions/b24988ac-6180-42a0-ab88-20f7382dd24c" -> null
- role_definition_name = "Contributor" -> null
- scope = "/subscriptions/subscription_id_hidden/resourceGroups/wcsccm-poc-rg" -> null
}
Plan: 0 to add, 0 to change, 4 to destroy.
╷
│ Warning: Resource targeting is in effect
│
│ You are creating a plan with the -target option, which means that the result of this plan may not represent all of the changes requested by the
│ current configuration.
│
│ The -target option is not for routine use, and is provided only for exceptional situations such as recovering from errors or mistakes, or when
│ Terraform specifically suggests to use it as part of an error message.
╵
────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
Note: You didn't use the -out option to save this plan, so Terraform can't guarantee to take exactly these actions if you run "terraform apply" now.
[root@vm:4 wcsccm_temp](git:wcsccm_refactor) #
Expected Behaviour
It should have marked only below two resources for deletion
azurerm_role_assignment.iam_role[1] will be destroyed
azurerm_linux_virtual_machine.vm[1] will be destroyed
Actual Behaviour
It is marking below four resources for deletion
azurerm_linux_virtual_machine.vm[1] will be destroyed
azurerm_role_assignment.iam_role[0] will be destroyed
azurerm_role_assignment.iam_role[1] will be destroyed
azurerm_role_assignment.iam_role[2] will be destroyed
Steps to Reproduce
Copy above terraform configuration into issue.tf file then hit below commands
-
Create one folder name 'count_issue'
-
Copy/Download JSON content from this file in count_issue folder env_config.json
-
Copy/download TF.txt configuration in count_issue folder count_issue.tf.txt
-
Rename above file from count_issue.tf.txt to count_issue.txt
-
Update tf file section from line 16 to 19.
-
Make sure Service principal should be able to provide RBAC assignments to VM.
-
Execute
terraform init -
Execute
terraform planand review plan for VM/RBAC addition for 3 vms -
Execute
terraform apply --auto-approve -
Verify all the resources are created as per JSON content
-
Hit below command for generating destroy plan
terraform plan -destroy -target=azurerm_linux_virtual_machine.vm[1] -
You should be able to see the Actual output, which is not as per Expected output. PSA sample output from my console
Important Factoids
No response
References
No response
Thanks for raising this issue. Seems the dependency-handling should be based on the index.
@neil-yechenwei
Thanks for your response. I tried adding the dependency azurerm_role_assignment.iam_role resource as below -
resource "azurerm_role_assignment" "iam_role" {
count = local.instance_count
scope = azurerm_resource_group.rg.id
role_definition_name = "Contributor"
principal_id = azurerm_linux_virtual_machine.vm[count.index].identity[0].principal_id
depends_on = [ azurerm_linux_virtual_machine.vm ]
}
and I tried recreating the entire infrastructure after adding the dependency. However, it is marking all the iam_role resources for deletion, which is still the issue.
For the count attribute, the behavior is expected. It is recommended to either use for_each or define the resources separately.