Search code examples
azureterraform-provider-azure

Terraform : Create multiple Azure Policies using for_each?


I want to create multiple Azure Policies and I don't want to create the policies one after another. I would like to use for_each to define multiple Azure Policies. How do I do this?

For example, I have the following Azure Policies defined separately which should be created using the for_each or in any other better way like powershell https://techcommunity.microsoft.com/t5/core-infrastructure-and-security/azure-enterprise-policy-as-code-a-new-approach/ba-p/3607843

// Deny creation of resource groups missing certain tags
resource "azurerm_policy_definition" "require-tag-owner-on-rg" {
  name                = "require-tag-owner-on-rg"
  policy_type         = "Custom"
  mode                = "All"
  display_name        = "Require tag 'owner' on resource group"
  management_group_name = var.management-group-name

  metadata = <<METADATA
    {
    "version": "1.0.0",
    "category": "Custom"
    }
METADATA

  policy_rule = <<POLICY_RULE
    {   
      "if": {
        "allOf": [
          {
            "field": "type",
            "equals": "Microsoft.Resources/subscriptions/resourceGroups"
          },
          {
            "field": "tags['owner']",
            "exists": "false"
          }
        ]
      },
      "then": {
        "effect": "deny"
      }
    }
POLICY_RULE

}

// Deny creation of resource except in EastUS
resource "azurerm_policy_definition" "only-deploy-in-eastus" {
  name                = "only-deploy-in-eastus"
  policy_type         = "Custom"
  mode                = "All"
  display_name        = "only-deploy-in-eastus"
  management_group_id = data.azurerm_management_group.parent-mg.id

  policy_rule = <<POLICY_RULE
    {
    "if": {
      "not": {
        "field": "location",
        "equals": "eastus"
      }
    },
    "then": {
      "effect": "Deny"
    }
  }
POLICY_RULE
}

Solution

  • I tried using "for_each" to create policies with definitions in terraform environment for your code as detailed below.

    terraform{
    required_providers {
         azurerm = {
           source = "hashicorp/azurerm"
           version = "3.37.0"
         }
       }
     }
       provider "azurerm" {
        features {}
     }
     resource "azurerm_resource_group" "RG" {
      name = "example"
      location = "EastUS"
      }
     resource "azurerm_policy_definition" "policy" {
       for_each = {
         policy1 = "Create"
         policy2 = "Use"
         policy3 = "New"
       }
       name     = each.key
       policy_type         = "Custom"
      mode                = "All"
      display_name        = each.value
      
      metadata = <<METADATA
        {
        "version": "1.0.0",
        "category": "Custom"
        }
    METADATA
      policy_rule = <<POLICY_RULE
        {   
          "if": {
            "allOf": [
              {
                "field": "type",
                "equals": "Microsoft.Resources/subscriptions/resourceGroups"
              },
              {
                "field": "tags['xxxxx']",
                "exists": "false"
              }
            ]
          },
          "then": {
            "effect": "deny"
          }
        }
    POLICY_RULE
    
    }
    
    

    terraform init:

    enter image description here

    terraform plan

    enter image description here

    terraform apply:

    enter image description here

    Created in portal after deployment:

    enter image description here