terraform-aws-modules: Create a VPC and EKS Cluster with the Official Community Modules
Reuse maintained modules instead of writing everything #
The community project terraform-aws-modules publishes the most downloaded modules for AWS: vpc, iam, s3-bucket, eks, security-group, rds, alb, lambda and many more. They encode years of fixes and options, and are documented in the Terraform registry (OpenTofu uses the same modules from its own registry).
The trade-off: you learn less about the underlying resources and depend on module upgrades. The AWS with Terraform series writes the resources by hand to teach them, which is the right way to learn. In production, a maintained module is often the better choice.
How to use a registry module #
module "vpc" {
source = "terraform-aws-modules/vpc/aws"
version = "~> 5.0"
name = "ditwl-pro"
cidr = "10.10.0.0/16"
azs = ["eu-west-1a", "eu-west-1b", "eu-west-1c"]
private_subnets = ["10.10.1.0/24", "10.10.2.0/24", "10.10.3.0/24"]
public_subnets = ["10.10.101.0/24", "10.10.102.0/24", "10.10.103.0/24"]
enable_nat_gateway = true
single_nat_gateway = true # cheaper, less available
enable_dns_hostnames = true
public_subnet_tags = {
"kubernetes.io/role/elb" = 1
}
private_subnet_tags = {
"kubernetes.io/role/internal-elb" = 1
}
tags = {
Environment = "pro"
ManagedBy = "opentofu"
}
}This single block creates the VPC, subnets, internet gateway, NAT gateway and route tables that take several tutorials to write by hand. The module outputs include vpc_id, private_subnets and public_subnets.
Always pin the version (~> 5.0 allows 5.x updates but not 6.0) and read the changelog before upgrading a major version, since module upgrades can recreate resources. Run plan and review it.
EKS cluster on top of the VPC #
module "eks" {
source = "terraform-aws-modules/eks/aws"
version = "~> 20.0"
cluster_name = "ditwl-pro"
cluster_version = "1.31"
vpc_id = module.vpc.vpc_id
subnet_ids = module.vpc.private_subnets
cluster_endpoint_public_access = true
enable_cluster_creator_admin_permissions = true
eks_managed_node_groups = {
default = {
instance_types = ["t3.medium"]
min_size = 2
max_size = 4
desired_size = 2
}
}
tags = {
Environment = "pro"
}
}The version numbers above are examples: check the current major version and the supported Kubernetes versions in the module documentation, because the inputs change between majors. The module creates the cluster, IAM roles, security groups, an OIDC provider and the managed node group. Connect to it with:
$ aws eks update-kubeconfig --name ditwl-pro --region eu-west-1
$ kubectl get nodes
To write the cluster by hand see Terraform EKS. To install add-ons such as an ingress controller use the Helm provider, and to deploy applications use Argo CD.
Other popular modules #
| Module | Use |
|---|---|
terraform-aws-modules/iam/aws |
Users, roles, policies, OIDC roles for GitHub (IAM) |
terraform-aws-modules/s3-bucket/aws |
Secure S3 buckets (S3) |
terraform-aws-modules/security-group/aws |
Security groups with predefined rules |
terraform-aws-modules/rds/aws |
RDS and Aurora (RDS) |
terraform-aws-modules/alb/aws |
Application and network load balancers |
terraform-aws-modules/lambda/aws |
Lambda with packaging and permissions (Lambda) |
Checklist before using a third-party module #
- Is it maintained, with recent releases and responses to issues?
- Does it pin provider versions reasonably?
- Read the code of the resources it creates: you are responsible for what it deploys.
- Pin the version and update deliberately.
- Scan it with security tools.
Cost #
The example creates a NAT gateway, an EKS control plane (charged per hour) and EC2 nodes. Estimate it with Infracost and run destroy when you finish.