Day 5 - Terraform Modules

Day 5 - Terraform Modules

Day 5 of TerraWeek

ยท

7 min read

Task 1

What are modules in Terraform and why do we need modules in Terraform?

๐Ÿ›‘ Terraform modules

A Terraform module is a set of configuration files organized in a specific directory. So, it implies that you can reuse them later with possible customizations without duplicating the resource blocks each time you require them, which is practical for big projects with complicated designs.

  • Terraform modules are reusable units of infrastructure configuration.

  • Modules encapsulate related resources and configurations as a single entity.

  • They promote code reusability, consistency, and standardization.

  • Modules abstract away complex configurations and implementation details.

  • They simplify the consumption of resources by providing a clear interface and inputs.

  • They improve code maintainability, readability, and scalability.

  • Modules can be versioned, allowing controlled changes and updates.

  • Versioning enables consistent deployments and easy rollbacks.

  • Modules facilitate collaboration among teams by providing a clear contract and interface.

The directory structure of a root module.

๐Ÿ›‘ Why do we need modules in Terraform

  • Organise Configuration: Easier to navigate, understand, and update your configuration

  • Encapsulate Configuration: Helps prevent unintended consequences

  • Re-use Configuration: Share modules that you have written with your team or the general public

  • Consistency: help to provide consistency in your configurations

What are the benefits of using modules in Terraform?

  • Reusability: Modules promote code reuse across projects, environments, or teams.

  • Consistency: Modules ensure consistent infrastructure configuration and management.

  • Abstraction: Modules abstract away complex configurations and implementation details.

  • Scalability: Modules allow easy replication and scaling of infrastructure resources.

  • Organization: Modules help organize and structure Terraform code.

  • Versioning: Modules can be versioned for controlled changes and rollbacks.

  • Collaboration: Modules facilitate teamwork and sharing of infrastructure resources.

  • Testing and Validation: Modules enable independent testing and validation of configurations.

  • Community Ecosystem: Access to a wide range of reusable modules from the Terraform community.


Task 2

Create/Define a module in Terraform to encapsulate reusable infrastructure configuration in a modular and scalable manner. E.g. EC2 instance in AWS, Resource Group in Azure, Cloud Storage bucket in GCP.

  • Here is the GitHub repo so you can check or copy what you need, terraweek-challenge/day5/

  • In root main.tf we will be adding our module. Our provider will be AWS, so add the following to our providers.tf. In variables.tf we have declared variables and got them from terraform.tfvars file.

      #This is terraform.tfvars file and other files u can get from github repo
      aws_region               = "us-east-1"
      ami                      = "<ami ID>"
      instance_type            = "t2.micro"
      instance_name            = "terraweek-day5"
      key_pair_name            = "TerraformKey"
    
  • After setting up all the files you can run the following commands.

  • Run the terraform init command to initialize Terraform.

  • Run terraform validate command to ensure there are no syntax errors.

  • Run terraform plan command to see what resources will be created.

  • Run the terraform apply command to apply the Terraform configuration and create the EC2 instance.

  • Now the instance is running and I have used a user-data file to install nginx, so nginx is also running.

  • Run the terraform destroy command to destroy the Terraform configuration and delete the EC2 instance.


Task 3

Dig into modular composition and module versioning.

๐Ÿ›‘ Modular Composition

In Terraform, modular composition means you can combine smaller and reusable modules together to create more complex infrastructure setups. This nesting capability allows you to build sophisticated deployments by integrating different modules. It promotes the reuse of code, enhances modularity, and makes your infrastructure configurations easier to manage and maintain.

To better understand modular composition, let's take a look at an example.

# main.tf

terraform {
  required_version = ">= 1.0.0"
}

module "vpc" {
  source     = "./vpc"
  vpc_cidr   = "10.0.0.0/16"
  subnet_cidr = "10.0.1.0/24"
}

module "ec2" {
  source        = "./ec2_instance"
  ami_id        = "ami-12345678"
  instance_type = "t2.micro"
  subnet_id     = module.vpc.example_subnet_id
}

output "instance_ip" {
  description = "Public IP address of the EC2 instance"
  value       = module.ec2.instance_ip
}

In this example, we are using subnet_id in the ec2 module.

By adopting modular composition, we can achieve the following benefits:

  • Reusability: Modules can be used across multiple Terraform configurations, enabling code reuse and reducing duplication.

  • Encapsulation: Modules encapsulate a specific functionality or component, making it easier to reason about and maintain infrastructure code.

  • Scalability: Modules can be scaled up or down based on your infrastructure needs, allowing for easy expansion or reuse of infrastructure components.

  • Separation of Concerns: Modules provide a clear separation of concerns, making it easier to manage and update specific parts of your infrastructure independently.

๐Ÿ›‘ Module versioning

Module versioning in Terraform allows you to control and manage the specific versions of modules used in your infrastructure code. It ensures that the same module version is consistently used across different deployments and team collaboration, promoting stability and predictability.

Terraform module versions can be specified using version constraints or exact versions. Version constraints define a range of acceptable versions, while exact versions ensure the use of a specific version. By locking module versions, you can prevent unexpected changes or updates to modules, ensuring consistent and reproducible deployments.

# main.tf

terraform {
  required_version = ">= 1.0.0"
}

module "example" {
  source  = "./example_module"
  version = "1.2.0"

  ami_id        = "ami-12345678"
  instance_type = "t2.micro"
}

output "instance_ip" {
  description = "Public IP address of the EC2 instance"
  value       = module.example.instance_ip
}

In this example, we specify the module "example" with a specific version 1.2.0. We also provide values for the required input variables ami_id and instance_type within the module block.

Module versioning helps in the following ways:

  • Reproducibility: Locking module versions ensures that the same versions are used in subsequent Terraform operations, enabling reproducible deployments.

  • Stability: By specifying specific versions or version constraints, you can prevent unexpected changes or updates to modules, promoting stability in your infrastructure.

  • Collaboration: Module versioning facilitates team collaboration by providing a consistent and controlled environment for working with shared infrastructure code.


Task 4

What are the ways to lock Terraform module versions? Explain with code snippets.

Locking Terraform module versions is essential to ensure consistency and stability in your infrastructure deployments. It helps maintain the integrity of your infrastructure by fixing the module versions used across different environments and preventing unintended changes.

There are multiple ways to lock Terraform module versions. Let's explore two common approaches:

  1. Using a Version Constraint in the Module Block: You can specify a version constraint directly in the module block of your Terraform configuration. This approach allows you to define the allowed range of versions for the module.

     module "example" {
       source  = "example/infrastructure/aws"
       version = "~> 1.0"  # Specifies a version constraint of 1.0 or higher, but below 2.0
     }
    

    In this code snippet, the module block references the module "example" and sets a version constraint of "~> 1.0". This constraint ensures that any version of the module equal to or higher than 1.0 but below 2.0 can be used.

  2. Using a Terraform Lock File: Terraform can generate a lock file, typically named terraform.lock.hcl, which records the exact versions of modules used in your configuration. The lock file can be manually created or automatically generated using the terraform init command.

     terraform {
       required_version = ">= 1.0.0"
    
       required_providers {
         aws = {
           source  = "hashicorp/aws"
           version = "3.57.0"
         }
       }
    
       modules {
         example = {
           source  = "example/infrastructure/aws"
           version = "1.2.0"
         }
       }
     }
    

    In this snippet, the lock file specifies the exact version of the module "example" and its source. The lock file ensures that Terraform always uses the recorded version, regardless of any changes in the module's source or configuration.

    Remember to commit the lock file to version control to maintain consistent module versions across deployments and team collaboration.


Thank you for reading!!
~Shreya Gupta

Great initiative by the #trainwithshubham community. Thank you Shubham Londhe

#devops #terraweek #terraform #terraformmodules

ย