Learn how to define and manage global variables in Terraform for efficient and reusable infrastructure code.
Terraform, by design, doesn't have a built-in "global variable" feature. However, there are several ways to manage and share values across your Terraform configurations, effectively achieving the same outcome. This article outlines five common approaches to handle values that you might typically want to use globally: using variables in the root module, passing variables to modules, leveraging Terraform Cloud or Enterprise workspaces, utilizing tools like Terragrunt or Terramate, and employing data sources for shared values. Each approach has its own strengths and is suited for different scenarios depending on your project's structure and specific needs.
While Terraform doesn't have a built-in concept of "global variables", you can achieve similar results using different approaches depending on your use case:
1. Variables in Root Module:
Define variables in a file like variables.tf
in your root module.
variable "region" {
default = "us-west-2"
}
Access these variables directly within any .tf
file in your root module.
resource "aws_instance" "example" {
region = var.region
}
2. Passing Variables to Modules:
Define variables in your root module's variables.tf
.
Pass these variables as arguments when calling modules.
module "my_module" {
source = "./modules/my-module"
region = var.region
}
Access passed variables within your module.
# Inside modules/my-module/main.tf
resource "aws_instance" "example" {
region = var.region
}
3. Terraform Cloud/Enterprise Workspaces:
Define variables at the workspace or project level in Terraform Cloud/Enterprise.
These variables are accessible within the specific workspace or project.
4. Tools like Terragrunt or Terramate:
These tools provide features like hierarchical configuration and global variables.
Terragrunt Example: Define variables in a terragrunt.hcl
file.
locals {
region = "us-west-2"
}
terraform {
source = "./modules/my-module"
}
inputs = {
region = local.region
}
5. Data Sources for Shared Values:
data "aws_ami" "example" {
most_recent = true
filter {
name = "name"
values = ["amzn-ami-hvm-*-x86_64-gp2"]
}
owners = ["amazon"]
}
resource "aws_instance" "example" {
ami = data.aws_ami.example.id
# ... other configurations
}
Remember to choose the approach that best suits your project structure and requirements.
This code demonstrates different ways to use "global variables" in Terraform. It shows how to define variables in the root module and access them in resource configurations. It also covers passing variables to modules, using Terraform Cloud/Enterprise workspaces, leveraging Terragrunt for variable management, and utilizing data sources like AWS SSM Parameter Store for shared values. Each approach provides a way to centralize and manage common configuration values, promoting code reusability and consistency across Terraform projects.
This document provides code examples for achieving "global variable" functionality in Terraform using different approaches.
1. Variables in Root Module:
variables.tf:
variable "region" {
default = "us-west-2"
}
variable "instance_type" {
default = "t2.micro"
}
main.tf:
resource "aws_instance" "example" {
ami = data.aws_ami.example.id
instance_type = var.instance_type
region = var.region
}
data "aws_ami" "example" {
most_recent = true
filter {
name = "name"
values = ["amzn-ami-hvm-*-x86_64-gp2"]
}
owners = ["amazon"]
}
2. Passing Variables to Modules:
root/variables.tf:
variable "region" {
default = "us-west-2"
}
root/main.tf:
module "my_module" {
source = "./modules/my-module"
region = var.region
}
modules/my-module/main.tf:
variable "region" {}
resource "aws_instance" "example" {
ami = data.aws_ami.example.id
instance_type = "t2.micro"
region = var.region
}
data "aws_ami" "example" {
most_recent = true
filter {
name = "name"
values = ["amzn-ami-hvm-*-x86_64-gp2"]
}
owners = ["amazon"]
}
3. Terraform Cloud/Enterprise Workspaces:
(This example demonstrates the concept, but you'll need to configure variables within your Terraform Cloud/Enterprise workspace.)
main.tf:
resource "aws_instance" "example" {
ami = data.aws_ami.example.id
instance_type = "t2.micro"
region = terraform.workspace # Accessing workspace variable
}
# ... other configurations
4. Terragrunt Example:
terragrunt.hcl:
locals {
region = "us-west-2"
}
terraform {
source = "./modules/my-module"
}
inputs = {
region = local.region
}
modules/my-module/main.tf:
variable "region" {}
resource "aws_instance" "example" {
ami = data.aws_ami.example.id
instance_type = "t2.micro"
region = var.region
}
# ... other configurations
5. Data Sources for Shared Values:
main.tf:
data "aws_ssm_parameter" "region" {
name = "/my-app/region"
}
resource "aws_instance" "example" {
ami = data.aws_ami.example.id
instance_type = "t2.micro"
region = data.aws_ssm_parameter.region.value
}
# ... other configurations
This example retrieves the region value from an AWS SSM Parameter Store parameter.
Remember to adapt these examples to your specific needs and choose the approach that best suits your project structure and requirements.
General Considerations:
Specific to Approaches:
Best Practices:
By understanding these nuances and following best practices, you can effectively manage shared values in your Terraform projects while maintaining a clean and maintainable codebase.
While Terraform lacks built-in global variables, you can achieve similar functionality through various methods:
| Approach | Description
In conclusion, while Terraform itself doesn't offer a dedicated "global variable" functionality, the platform's flexibility allows for several effective workarounds. By employing techniques such as defining variables in the root module, strategically passing variables to modules, utilizing Terraform Cloud/Enterprise workspaces, integrating tools like Terragrunt or Terramate, or leveraging data sources for shared values, developers can achieve the desired outcome of managing and sharing values across their Terraform configurations. The key is to select the approach that best aligns with the specific needs and structure of your project, ensuring a balance between centralized management and modularity. As your project scales, remember to prioritize clear documentation and consistent naming conventions to maintain a clean and understandable codebase. By understanding these different approaches and their respective strengths, you can effectively manage shared values in your Terraform projects, promoting code reusability and consistency without compromising the platform's core principles of modularity and encapsulation.