Skip to main content

Optional Configuration Blocks in Terraform

Table of Contents

A Terraform dynamic block lets you add configuration blocks to resources. Depending on a sequence of values, you can add as many configuration blocks as you like, even wholly omitting them.

The for_each argument is the primary driver of dynamic blocks. Because of this, we need to write extra code for a simple use case, such as an optional block. To illustrate, we desire the effect of a flag argument, which is unsupported by Terraform:

# Desired
dynamic "config_block" {
    create = local.create_config
    content {
        ...
    }
}

# Actual
dynamic "config_block" {
    for_each = local.create_config? [1] : []
    content {
        ...
    }
}

Fortunately, Terraform has a feature to support such behaviour with splat expressions. They even documented that feature. This code is equivalent to the previous illustrations and is much cleaner.

dynamic "config_block" {
    for_each = local.create_config[*]
    content {
        ...
    }
}

However, there’s one catch: the control variable must be nullable (i.e., it can be null or any other type). There are many ways to generate nullables. Here are some examples:

  • Call the try function

    locals {
      create_config = try(..., null)
    }
    
  • Declare one of the attributes of an input variable with an object type to optional

    var "config" {
      type = object({
        maybe_id = optional(string)
      })
    }
    
    locals {
      create_config = var.config.maybe_id
    }
    

References #