hashicorp / terraform-provider-azurerm

Terraform provider for Azure Resource Manager
https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs
Mozilla Public License 2.0
4.61k stars 4.65k forks source link

Azure Firewall replaced due to capitalization of SubnetId resource group #11043

Closed aglees closed 3 years ago

aglees commented 3 years ago

Community Note

Terraform (and AzureRM Provider) Version

terraform -vTerraform v0.14.5
+ provider registry.terraform.io/hashicorp/azuread v1.4.0
+ provider registry.terraform.io/hashicorp/azurerm v2.52.0
+ provider registry.terraform.io/hashicorp/helm v2.0.3
+ provider registry.terraform.io/hashicorp/kubernetes v2.0.3
+ provider registry.terraform.io/hashicorp/random v2.3.1

Affected Resource(s)

Terraform Configuration Files

resource "azurerm_firewall" "afw" {
  name                = "${var.env}-afw"
  location            = var.location
  resource_group_name = var.resource_group_name
  tags                = local.tags

  zones = var.availability_zones

  ip_configuration {
    name = "configuration"
    subnet_id            = data.azurerm_subnet.afw_subnet.id #<-- this was a hack before the issue
    #subnet_id            = azurerm_subnet.afw_subnet.id #<--- this used to work
    #subnet_id            = replace(data.azurerm_subnet.afw_subnet.id, "ppe1-resources", "PPE1-RESOURCES") #<-- HACK
    #subnet_id            = replace(azurerm_subnet.afw_subnet.id, "ppe1-resources", "PPE1-RESOURCES") #<-- alternate HACK
    public_ip_address_id = var.afw_public_ip_id
  }

  dynamic "ip_configuration" {
    for_each = var.afw_public_ip_prefix_map

    content {
      name                 = ip_configuration.key
      public_ip_address_id = ip_configuration.value
    }
  }

}

Debug Output

Panic Output

Expected Behaviour

Terraform doesn't want to destroy and re-create the Azure Firewall

Actual Behaviour

Terraform wants to destroy and re-create the Azure Firewall

# module.vnet.azurerm_firewall.afw must be replaced
-/+ resource "azurerm_firewall" "afw" {
      - dns_servers         = [] -> null
      ~ id                  = "/subscriptions/{subscription_id}/resourceGroups/ppe1-resources/providers/Microsoft.Network/azureFirewalls/ppe1-afw" -> (known after apply)
        location            = "westeurope"
        name                = "ppe1-afw"
        resource_group_name = "ppe1-resources"
      ~ sku_name            = "AZFW_VNet" -> (known after apply)
      ~ sku_tier            = "Standard" -> (known after apply)
        threat_intel_mode   = "Alert"
        zones               = [
            "1",
            "2",
            "3",
        ]

      ~ ip_configuration {
            name                 = "configuration"
          ~ private_ip_address   = "{PRIVATE_IP}" -> (known after apply)
            public_ip_address_id = "/subscriptions/{subscription_id}/resourceGroups/ppe-mgmt-ips/providers/Microsoft.Network/publicIPAddresses/ppe1-ip-afw"
          ~ subnet_id            = "/subscriptions/{subscription_id}/resourceGroups/PPE1-RESOURCES/providers/Microsoft.Network/virtualNetworks/ppe1-app-vnet/subnets/AzureFirewallSubnet" -> "/subscriptions/{subscription_id}/resourceGroups/ppe1-resources/providers/Microsoft.Network/virtualNetworks/ppe1-app-vnet/subnets/AzureFirewallSubnet" # forces replacement
        }
      ~ ip_configuration {
            name                 = "ppe1-ip-prefix-afw1"
          + private_ip_address   = (known after apply)
            public_ip_address_id = "/subscriptions/{subscription_id}/resourceGroups/ppe-mgmt-ips/providers/Microsoft.Network/publicIPAddresses/ppe1-ip-prefix-afw1"
        }
      ~ ip_configuration {
            name                 = "ppe1-ip-prefix-afw2"
          + private_ip_address   = (known after apply)
            public_ip_address_id = "/subscriptions/{subscription_id}/resourceGroups/ppe-mgmt-ips/providers/Microsoft.Network/publicIPAddresses/ppe1-ip-prefix-afw2"
        }
    }

Steps to Reproduce

  1. terraform apply

Important Factoids

References

Welasco commented 3 years ago

I have the same issue and it try destroy the firewall for any change in any dependency that azurerm_firewall has. Even for a simple tag if you have a tag in any resource that azurerm_firewall depends on it will force the recreation of the whole firewall. I tested multiple times and it's always the same behavior. If you remove all dependencies and manually pass everything as a string it stop happening. Definitely it's a bug.

magodo commented 3 years ago

@aglees Thank you for submitting this! I've tried to reproduce it locally with the same provider version you've used (v2.52.0), with the configuration in the doc site, but can't reproduce it. Would you please give me some more detailed steps to reproduce this? A rough guess is that the firewall has been managed outside of Terraform (e.g. via other clients, like Portal/CLI), which might not conform to the Terraform convention about resource IDs and send out the resource group segment in upper case, the service team then reserve the case. Later, when you try to manage it back in Terraform, it gives you the diff.

@Welasco IIRC, once the subnet is used by a firewall, it is not able to be updated, otherwise, you'll get InUseSubnetCannotBeUpdated error. Would you also kindly provide me the detailed steps that you've done, which will cause the firwall to be replaced?

tombuildsstuff commented 3 years ago

Closing this out since we've not heard back here - if your able to provide the information that @magodo has requested above then we can take another look, however.

github-actions[bot] commented 3 years ago

I'm going to lock this issue because it has been closed for 30 days ⏳. This helps our maintainers find and focus on the active issues. If you have found a problem that seems similar to this, please open a new issue and complete the issue template so we can capture all the details necessary to investigate further.