Terraform modules are the fundamental unit of reuse and abstraction in infrastructure as code. A module is any directory containing Terraform configuration files — every configuration you have written so far is technically a module, called the root module. What makes a module useful as a component for reuse is the deliberate design of its interface: well-typed input variables that encode assumptions and constraints, outputs that expose precisely the information callers need, and a consistent internal structure that is easy for other engineers to read, debug and extend. Without modules, large Terraform codebases become monolithic files where every environment's configuration duplicates the same networking, compute and database patterns with minor variations. With well-designed modules, provisioning a complete new environment means instantiating five or ten module calls with environment-specific variable values — the infrastructure pattern is written once, tested once, and reused everywhere.
The Terraform Registry (registry.terraform.io/modules) hosts thousands of community and verified modules that implement common infrastructure patterns — VPCs, EKS clusters, RDS databases, ALBs. Using Registry modules for standard patterns (rather than writing them from scratch) is the correct first instinct: HashiCorp-verified modules are maintained by the cloud providers themselves (the AWS VPC module is maintained by HashiCorp with input from AWS), battle-tested across thousands of organisations, and updated with each provider API change. However, most organisations that use Terraform at scale maintain their own internal module registry — a Git repository of modules that implement the company's specific patterns, security requirements and naming conventions. Understanding both the Registry module consumption pattern and the internal module authoring pattern is essential for production Terraform work.