Skip to content

Terraform Modules

A Terraform module is a collection of configuration files organized together to encapsulate reusable infrastructure logic. Modules promote consistency, enforce best practices, reduce duplicated code, and speed up development.

Terraform modules can be fetched either from the public Terraform Registry (only verified and official modules are highlighted during search) or from private registries.

Verified modules are reviewed by HashiCorp, actively maintained, and guaranteed to stay compatible with both Terraform and their respective providers. They are marked with a special badge.


Public Modules

The Terraform Registry is natively integrated into Terraform.

A registry module follows the format: <NAMESPACE>/<NAME>/<PROVIDER>

Example:

module "consul" {
    source = "hashicorp/consul/aws"
    version = "0.1.0"
}

Private Modules

Private modules use the format: <HOSTNAME>/<NAMESPACE>/<NAME>/<PROVIDER>

Example:

module "consul" {
    source = "app.terraform.io/example_corp/consul/aws"
    version = "0.1.0"
}

To use private modules, you must authenticate with Terraform Cloud using one of the following:

  • Run terraform login
  • Create an user API token and manually configure credentials in the Terraform CLI configuration file.

When you run terraform init, Terraform automatically downloads and caches all modules defined in the configuration.


Publishing Modules

Anyone can publish modules to the Terraform Registry. Published modules support:

  • Versioning
  • Auto-generated documentation
  • Browsable version history
  • Examples
  • Automatic README rendering

To be recognized as a valid public module (within terraform-aws-modules), your repository must follow the naming convention: terraform-<PROVIDER>-<NAME> (for example: terraform-aws-vpc).

Notes:

  • In order to publish a module you have to connect on Terraform Module Registry with your GitHub account
  • New releases are published automatically whenever you push new semantically versioned Git tags.

Standard Module Structure

|- README.md
|- LICENSE
|- main.tf
|- variables.tf
|- outputs.tf
|- ...
|- modules/
|   |- nestedA/
|   |   |- README.md
|   |   |- main.tf
|   |   |- variables.tf
|   |   |- outputs.tf
|   |- nestedB/
|   |- ...
|- examples/
|   |- exampleA/
|   |   |- main.tf
|   |- exampleB/
|   |- ...

Rules and Guidelines

  • A submodule with a README is considered publicly usable by external users.
  • A submodule without a README is considered for internal use only.
  • Avoid using relative paths (../moduleA) when referencing modules. Prefer registry sources or properly defined module registries.
  • Include examples when publishing modules - they improve documentation quality and user adoption.