In the world of Infrastructure as Code (IaC), Terraform has emerged as a powerful tool for managing infrastructure resources. As your Terraform codebase grows, managing monolithic code can become challenging. In this advanced-level blog post, we will explore the process of moving Terraform modules into separate Git repositories and referencing these modules across multiple repositories. This approach can help you achieve better code organization, reusability, and collaboration in your infrastructure provisioning projects.

Why Modularize Terraform Code?

Modularization is a fundamental concept in Terraform. It allows you to break down your code into reusable, testable, and maintainable components. As your Terraform project evolves, modularization can help in several ways:

  • Reusability: Modules can be shared across different projects.
  • Maintainability: Isolating components makes it easier to update, test, and troubleshoot.
  • Collaboration: Teams can work on different parts of the infrastructure independently.

Moving Terraform Modules into Separate Repositories

Create a New Git Repository

Assuming you have an existing Terraform module within your project, the first step is to create a new Git repository for the module. You can use platforms like GitHub, GitLab, or Bitbucket.

1
2
3
4
5
6
7
8
# Create a new Git repository on GitHub
# (Replace 'module-name' with your actual module name)
git init
git add .
git commit -m "Initial commit"
git branch -M main
git remote add origin https://github.com/yourusername/module-name.git
git push -u origin main

Configure the Module

Inside the module’s repository, you should have a well-structured module with a main.tf, variables.tf, and outputs.tf file. Make sure to define the module correctly in your Terraform code:

1
2
3
4
5
6
7
module "example" {
  source = "git::https://github.com/yourusername/module-name"

  # Specify input variables
  var1 = "value1"
  var2 = "value2"
}

Versioning

It’s crucial to version your modules to ensure consistency and avoid unexpected changes. Consider using Git tags to specify module versions.

1
2
3
# Create a tag for version 1.0.0
git tag -a v1.0.0 -m "Version 1.0.0"
git push origin v1.0.0

Referencing Modules from Different Repositories

Now, let’s discuss how to reference these modules in other Terraform configurations.

Terraform Module Sources

In your main Terraform configuration, specify the source of the module using the Git URL and the desired version.

1
2
3
4
5
6
7
module "example" {
  source = "git::https://github.com/yourusername/module-name?ref=v1.0.0"

  # Specify input variables
  var1 = "value1"
  var2 = "value2"
}

Referencing a Specific Directory in a Module

To refer to a specific folder within a module, you can specify the folder path in the module source URL. This allows you to use only a specific subdirectory within the module’s repository. Here are some code examples to demonstrate how to do this:

Let’s assume your module repository has the following structure:

1
2
3
4
5
6
7
github.com/yourusername/module-repo/
    └── terraform
        └── modules
            └── aws_asg_launch_template
                ├── main.tf
                ├── variables.tf
                ├── outputs.tf

You can reference the my-module subdirectory in your main Terraform configuration as follows:

1
2
3
4
5
6
7
module "example" {
  source = "git::https://github.com/yourusername/module-repo//terraform/modules/aws_asg_launch_template?ref=v1.0.0"
  
  # Specify input variables
  var1 = "value1"
  var2 = "value2"
}

In the example above, you specify the path to the my-module folder in your module source URL. This way, Terraform will use only the resources defined in that subdirectory of the module.

This approach allows you to isolate and reuse specific components of a module, making it more flexible and modular.

Authentication

If your Git repository is private, you might need to set up authentication. This can be done using personal access tokens, SSH keys, or other authentication methods, depending on the Git hosting platform.

Benefits of This Approach

Moving Terraform modules into separate Git repositories offers several advantages:

  • Improved Collaboration: Different teams or projects can use and contribute to modules independently.
  • Clear Versioning: Each module has its version, ensuring consistent infrastructure provisioning.
  • Simplified Terraform Codebase: The main configuration is cleaner, with less module code clutter.
  • Encourages Best Practices: You can enforce strict module structure and maintainability.

Last Thoughts

Advanced Terraform users often face the challenge of managing complex infrastructure projects. Modularizing your code and separating modules into distinct Git repositories can provide a powerful solution. This approach enhances collaboration, code reusability, and maintainability while ensuring version consistency in your infrastructure as code projects. So, consider making this transition as your Terraform projects grow, and embrace the advantages it offers.