Last Updated on August 7, 2025 by Arnav Sharma
To loop over a list in Terraform, you can use a for loop within a resource or module definition, or in any other part of your Terraform code where iteration might be necessary. Here’s a general approach to using a for loop in Terraform:
Example 1: Creating Multiple Azure Virtual Machines
In this example, we’ll create multiple Azure virtual machines (VMs) using for_each. Let’s assume we have a list of other resources like VM names.
locals {
vm_names = ["vm1", "vm2", "vm3"]
}
resource "azurerm_virtual_machine" "example" {
for_each = toset(local.vm_names)
name = each.value
location = "East US"
resource_group_name = azurerm_resource_group.example.name
network_interface_ids = [azurerm_network_interface.example[each.key].id]
vm_size = "Standard_F2"
# Other necessary configurations...
}
Here, each.value represents each VM name in the list.
Example 2: Creating Multiple Network Interfaces with Different Settings
If you have a list of settings for network interfaces and want to create a distinct network interface for each set of settings:
locals {
nics_settings = [
{ name = "nic1", ip_configuration_name = "ipconfig1" },
{ name = "nic2", ip_configuration_name = "ipconfig2" },
{ name = "nic3", ip_configuration_name = "ipconfig3" }
]
}
resource "azurerm_network_interface" "example" {
for_each = { for nic in local.nics_settings : nic.name => nic }
name = each.value.name
location = "East US"
resource_group_name = azurerm_resource_group.example.name
ip_configuration {
name = each.value.ip_configuration_name
subnet_id = azurerm_subnet.example.id
private_ip_address_allocation = "Dynamic"
# Other configurations...
}
}
In this example, each network interface is configured with different settings based on the list of nics_settings.
Example 3: Using count to Create Multiple Storage Accounts
Here, we’ll create a specified number of Azure storage accounts using the count argument:
variable "storage_account_count" {
description = "Number of storage accounts to create"
default = 3
}
resource "azurerm_storage_account" "example" {
count = var.storage_account_count
name = "storageaccount${count.index}"
resource_group_name = azurerm_resource_group.example.name
location = "East US"
account_tier = "Standard"
account_replication_type = "LRS"
# Other configurations...
}
In this case, count.index is used to create a unique name for each storage account.
Note:
- Resource Dependencies: When creating multiple resources that depend on each other (like VMs and their network interfaces), ensure that your configuration accounts for these dependencies.
- State Management: Be mindful of how Terraform manages state. Using
for_eachwith a map or a set can make your infrastructure more resilient to changes in the list, as opposed to usingcount, which relies on the order of the list. - Azure Provider Version: Ensure that you are using a compatible version of the Azure provider for Terraform, as some features and resources depend on the provider version.