> ## Documentation Index
> Fetch the complete documentation index at: https://notes.kodekloud.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Introduction

> Explains Terraform advanced constructs like locals, dynamic blocks, built-in functions, and best practices for building scalable, maintainable, production ready modules

Welcome to the next module: Advanced Constructs in Terraform.

So far you’ve learned variables, resources, simple expressions, and basic iterations. This lesson introduces constructs that make Terraform scalable, maintainable, and production-ready. We’ll cover how to compute reusable values, generate nested blocks programmatically, use built-in functions to transform data safely, and make practical decisions about when and how to apply these features.

This module focuses on four key concepts:

| Concept                          | Purpose                                                                                                 | Quick example                                          |
| -------------------------------- | ------------------------------------------------------------------------------------------------------- | ------------------------------------------------------ |
| Locals                           | Define derived, reusable values inside a module to reduce duplication and centralize naming/formatting. | `locals { env = "${var.project}-${var.environment}" }` |
| Dynamic blocks                   | Programmatically generate repeated nested configuration blocks (e.g., multiple ingress rules).          | See dynamic block example below                        |
| Built-in functions               | Transform and validate data safely (`join`, `concat`, `coalesce`, `lookup`, `jsonencode`, etc.).        | `join(", ", var.subnets)`                              |
| Decision-making & best practices | When to compute locally, how to design module boundaries, and how to keep code readable and testable.   | Guidance in the Best practices section                 |

1. Locals\
   Locals let you define computed, reusable values inside a module. Treat them as module-level constants derived from inputs. Use locals to:

* Consolidate repeated logic (formatting, naming, derived IDs).
* Simplify complex expressions (combinations of `for` expressions and conditional logic).
* Reduce duplication to make HCL easier to read and maintain.

Example: simple local for an environment-based name

```hcl theme={null}
locals {
  env_prefix = "${var.project}-${var.environment}"
  common_tags = {
    Project = var.project
    Env     = var.environment
  }
}
```

<Callout icon="lightbulb" color="#1CB2FE">
  Use locals when a value is derived from inputs and reused in multiple places. Locals are evaluated per-module and do not create additional state or resources.
</Callout>

2. Dynamic blocks\
   Dynamic blocks generate repeated nested blocks inside resources or modules, based on input collections. They prevent copy-pasting when the number of nested blocks varies.

Example: generating multiple `ingress` rules from a variable list

```hcl theme={null}
resource "aws_security_group" "example" {
  name = "${local.env_prefix}-sg"

  dynamic "ingress" {
    for_each = var.ingress_rules
    content {
      from_port   = ingress.value.from
      to_port     = ingress.value.to
      protocol    = ingress.value.protocol
      cidr_blocks = ingress.value.cidr_blocks
    }
  }
}
```

<Frame>
  <img src="https://mintcdn.com/kodekloud-c4ac6d9a/9l60TCpe5-axPZIp/images/Terraform-On-Azure/Advanced-Constructs/Introduction/terraform-introduction-locals-dynamic-blocks.jpg?fit=max&auto=format&n=9l60TCpe5-axPZIp&q=85&s=98f86fd5abdb4f1ba7d9a53b336a829f" alt="The image shows an introduction slide with two points about Terraform configurations: using locals for reusable values and applying dynamic blocks for nested resource configurations." width="1920" height="1080" data-path="images/Terraform-On-Azure/Advanced-Constructs/Introduction/terraform-introduction-locals-dynamic-blocks.jpg" />
</Frame>

<Callout icon="warning" color="#FF6B6B">
  Avoid overusing dynamic blocks to hide complex logic. If dynamic generation makes the configuration hard to read, prefer an explicit approach or refactor into a smaller module with clear inputs.
</Callout>

3. Built-in functions\
   Terraform’s built-in functions help you inspect and transform data safely. Common ones include:

* `join(separator, list)` — join list elements
* `concat(list1, list2)` — concatenate lists
* `coalesce(val1, val2, ...)` — return the first non-empty value
* `lookup(map, key, default)` — safe map lookup
* `jsonencode(value)` — encode an HCL value as JSON

Examples:

```hcl theme={null}
output "subnets_csv" {
  value = join(", ", var.subnet_ids)
}

locals {
  instance_name = coalesce(var.instance_name, "default-${var.environment}")
  policy_json   = jsonencode(local.policy_map)
}
```

4. Decision-making and best practices\
   Apply these constructs to improve readability and maintainability, not to obscure intent. Key guidelines:

* Compute values locally when they’re derived from module inputs and used in several places.
* Keep module APIs (inputs/outputs) explicit; avoid hiding important behavior inside complex locals or dynamic generation.
* Favor small, focused modules that are easy to test and reason about.
* Use built-in functions to write defensive expressions that tolerate optional or missing inputs.

Quick checklist:

* Are derived values used more than once? Use `locals`.
* Is the nested block count variable (and simple)? Use `dynamic`.
* Does complexity harm readability? Consider refactoring into a module.
* Can you write expressions that survive missing inputs? Use functions like `coalesce` and `lookup`.

Further reading and references

* [Terraform: Locals](https://www.terraform.io/language/values/locals)
* [Terraform: Dynamic Blocks](https://www.terraform.io/language/expressions/dynamic-blocks)
* [Terraform: Functions](https://www.terraform.io/language/functions)
* [Terraform best practices and module design patterns](https://www.terraform.io/docs/extend/best-practices/index.html)

In the following sections we’ll explore each concept with detailed examples and patterns that are proven in real-world Terraform projects.

<CardGroup>
  <Card title="Watch Video" icon="video" cta="Learn more" href="https://learn.kodekloud.com/user/courses/terraform-on-azure/module/4fafc188-5a1a-4dbf-8fa0-50e3f00a270d/lesson/aedc3cda-5080-4389-a97f-f4aa99ff8905" />
</CardGroup>
