- What is Terraform For Expression?
- Syntax of a Terraform for Expression
- How to Use For Expressions in Terraform
- Final Thoughts
As infrastructure as code (IaC) continues to evolve, managing complex cloud environments efficiently is more important than ever. Terraform, a widely adopted IaC tool, simplifies cloud infrastructure provisioning, and its flexibility is further enhanced through expressions like the powerful for
loop.
In this blog, we will explore how Terraform's for
expression can help transform collections with ease, allowing you to streamline infrastructure configuration. By breaking down the syntax and providing real-world examples, you’ll learn how to filter, mutate, and group resources dynamically. Whether you're managing instances or organizing cloud environments, this guide will give you the tools to handle it all programmatically.
What is Terraform For Expression?
The for
expression in Terraform is used to iterate over collections, such as lists or maps, to transform or filter elements. It helps create new lists or maps from existing ones by applying an expression to each element. This is especially useful for simplifying repetitive tasks and creating dynamic infrastructure configurations.
Syntax of a Terraform for Expression
for
expressions in Terraform provide a flexible way to transform and filter collections, whether they are lists, sets, or maps. Below are the syntaxes for both types of outputs—lists and maps—with examples.
1. Syntax: When the Output is a List
[for item in var.collection : transformation if condition]
-
var.collection
: The list or set you are iterating over. -
transformation
: The operation or logic applied to each item in the collection, such as accessing properties, applying a function, or performing calculations. -
if condition
: (Optional) A filtering condition to include only the items that satisfy the condition.
Example:
[for instance in aws_instances : upper(instance.name) if instance.status == "running"]
In this example, Terraform creates a list of instance names in uppercase, but only for instances where status
is "running"
.
2. Syntax: When the Output is a Map
{for key, value in var.map : key => transformation if condition}
-
var.map
: The map being iterated over. -
key => transformation
: Defines the key-value pair for the new map.key
remains unchanged, whiletransformation
applies logic to thevalue
. -
if condition
: (Optional) A filtering condition to include only key-value pairs that meet the condition.
Example:
{for name, instance in aws_instances : name => length(instance.tags) if instance.status == "running"}
In this example, Terraform generates a new map where the name
remains the same, but the value is the number of tags associated with each instance
. This is only done for instances with a "running"
status.
How to Use For Expressions in Terraform
In Terraform, for
expressions are powerful tools used to transform collections. There are three main types of transformations that for
expressions enable:
- Filtration
- Mutation
- Grouping
Let's explore each of these with examples to understand how they work.
1. Filtration of a Collection Based on a Condition
Filtration selectively includes only certain elements in a new collection based on a condition.
Variable Block with Defaults:
variable "aws_instances" {
default = [
{ id = "i-001", status = "running" },
{ id = "i-002", status = "stopped" },
{ id = "i-003", status = "running" }
]
type = list(object({
id = string
status = string
}))
}
For Expression Example:
output "running_instance_ids" {
value = [for instance in var.aws_instances : instance.id if instance.status == "running"]
}
Explanation:
This filters the aws_instances
variable, creating a list of id
s only for instances that have the status "running"
. In this case, the output would be ["i-001", "i-003"]
.
2. Mutation of a Collection Based on a Condition
Mutation modifies each element in the collection, often based on a condition.
Variable Block with Defaults:
variable "users" {
default = [
{ name = "Alice", is_active = true },
{ name = "Bob", is_active = false },
{ name = "Charlie", is_active = true }
]
type = list(object({
name = string
is_active = bool
}))
}
For Expression Example:
output "active_user_names" {
value = [for user in var.users : upper(user.name) if user.is_active]
}
Explanation:
This expression loops through the users
collection, converts the name
of active users (is_active == true
) to uppercase, and returns a list of the transformed names. The result would be ["ALICE", "CHARLIE"]
.
3. Grouping of a Collection Based on a Condition
Grouping creates a map that organizes elements based on a specific key or condition.
Variable Block
First, define the variable for projects
, holding the project details like region and environments.
variable "projects" {
type = map(object({
region = string
environments = list(string)
}))
default = {
customer_api = {
region = "australiasoutheast"
environments = ["dev", "uat", "prd"]
}
partner_api = {
region = "australiasoutheast"
environments = ["dev", "prd"]
}
internal_api = {
region = "australiaeast"
environments = ["prd"]
}
payments_api = {
region = "norwayeast"
environments = ["dev", "tst", "uat", "sit", "stg", "prd"]
}
returns_api = {
region = "norwayeast"
environments = ["dev", "uat", "prd"]
}
refunds_api = {
region = "norwayeast"
environments = ["dev", "uat", "prd"]
}
}
}
Grouping Projects by Region
Use a for
expression to dynamically group projects based on their region, creating a map where the key is the region, and the value is a list of project names.
output "projects_grouped_by_region" {
value = {
for project, details in var.projects :
details.region => concat(
lookup({for project, details in var.projects : details.region => []}, details.region, []),
[project]
)
}
}
Explanation
Variable Block: The
projects
variable is amap
where the key is the project name, and the value is an object containingregion
andenvironments
. This structure makes it flexible for real-world scenarios.for
Expression in Output: The output groups the projects based on theirregion
. We useconcat()
to collect all projects with the same region into a list. The expression is designed to ensure each region groups all relevant projects.
Example Output
This output
will group the projects by region, showing something like this:
projects_grouped_by_region = {
"australiaeast" = ["internal_api"]
"australiasoutheast" = ["customer_api", "partner_api"]
"norwayeast" = ["payments_api", "returns_api", "refunds_api"]
}
Final Thoughts
Terraform’s for
expression is a game-changer for anyone looking to automate complex infrastructure transformations. With its ability to filter, mutate, and group collections dynamically, you can tackle even the most intricate use cases with elegance and simplicity. From optimizing resource management to enhancing infrastructure readability, the examples we've discussed show how for
expressions can transform not just collections, but also how you approach infrastructure as a whole. Happy Deploying!!!
Top comments (0)