AWS Terraform Diagnostics
In today’s post we will setup 2-tier application on AWS with the help of Terraform. A Tool for Infrastructure as Code (IaC) is the practice of managing and provisioning infrastructure (e.g., servers, networks, databases) through machine-readable configuration files rather than manual processes. This approach treats infrastructure the same as software, enabling automation, consistency, and version control. More detail about Terraform is available thier offical website as well.
Let’s start and setup 2-tier architecture by using following AWS Services.
- Region
- VPC
- Availability Zone
- Public Subnet
- Private Subnet
- Route table
- Internet Gateway
- EC2 Instance
Let’s start by setting up the architecture, selecting the AWS region based on your location. In the code snippet, configure the Terraform AWS provider, specify its version, and set the AWS region to ap-southeast-1.
Setup AWS VPC and specific CIDR block 192.168.0.0/16.
Setup public subset along with AWS availability zone. You need to select map_public_ip_on_launch property set to “True”.
Now setup private subset with the same AWS availability zone. But this time set map_public_ip_on_launch property set to “False”.
Now setup Route Table and attach the VPC using its id property.
Now associate public subnets with the previously created route table.
Now create Internet Gateway and set its vpc_id property with VPC id.
To access the Bastion host machine, we need to configure a Security Group that allows TCP access on ports 22 and 80 from any source.
To access the private EC2 instance, we need to configure an additional Security Group, permitting TCP port 22 access exclusively from the Bastion Host’s Security Group.
Set up a new Bastion host in the public subnet, customizing the EC2 instance specifications to suit your needs.
Now create the new private host machine in the private subnet, specify the EC2 instance as per your requirement.
Up to this point your 2-tier architecture is completed and for your help I’m sharing complete code snippent of the Terraform.
# Select AWS Provider and Region
terraform {
required_providers {
aws = {
source = "hashicorp/aws"
version = "~>4"
}
}
}
provider "aws" {
region = "ap-southeast-1"
}
# Setup AWS VPC
resource "aws_vpc" "two-tier-vpc" {
cidr_block = "10.0.0.0/16"
tags = {
Name = "two-tier-vpc"
}
}
# Configure public subnet with availability zone
resource "aws_subnet" "two-tier-public-subnet" {
vpc_id = aws_vpc.two-tier-vpc.id
map_public_ip_on_launch = "true"
cidr_block = "192.168.1.0/24"
availability_zone = "ap-southeast-1a"
tags = {
Name = "two-tier-public-subnet"
}
}
# Configure private subnet with availability zone
resource "aws_subnet" "two-tier-private-subnet" {
vpc_id = aws_vpc.two-tier-vpc.id
map_public_ip_on_launch = "false"
cidr_block = "192.168.2.0/24"
availability_zone = "ap-southeast-1a"
tags = {
Name = "two-tier-private-subnet"
}
}
# Configure Route Table
resource "aws_route_table" "two-tier-Route_Table" {
vpc_id = aws_vpc.two-tier-vpc.id
route {
gateway_id = aws_internet_gateway.two-tier-igw.id
cidr_block = "0.0.0.0/0"
}
tags = {
Name = "two-tier-rt"
}
}
#Configure Route Table Association
resource "aws_route_table_association" "two-tier-rt-as-1" {
subnet_id = aws_subnet.two-tier-pub-sub-1.id
route_table_id = aws_route_table.two-tier-Route_Table.id
}
#Setup Internet Gateway
resource "aws_internet_gateway" "two-tier-igw" {
vpc_id = aws_vpc.two-tier-vpc.id
tags = {
Name = "two-tier-igw"
}
}
#Setup security group for bastion host machine
resource "aws_security_group" "two-public-sg" {
vpc_id = aws_vpc.two-tier-vpc.id
name = "two-tier-ec2-sg"
description = "Allow traffic from VPC"
depends_on = [
aws_vpc.two-tier-vpc,
]
egress {
to_port = 0
protocol = "-1"
from_port = 0
cidr_blocks = [
"0.0.0.0/0",
]
}
ingress {
to_port = 0
protocol = "-1"
from_port = 0
}
ingress {
to_port = 80
protocol = "tcp"
from_port = 80
cidr_blocks = [
"0.0.0.0/0",
]
}
ingress {
to_port = 22
protocol = "tcp"
from_port = 22
cidr_blocks = [
"0.0.0.0/0",
]
}
tags = {
Name = "two-public-sg"
}
}
#Setup security group for private server
resource "aws_security_group" "two-private-sg" {
vpc_id = aws_vpc.two-tier-vpc.id
name = "two-tier-db-sg"
description = "allow traffic from internet"
egress {
to_port = 0
protocol = "-1"
from_port = 0
cidr_blocks = [
"0.0.0.0/0",
]
}
ingress {
to_port = 3306
protocol = "tcp"
from_port = 3306
cidr_blocks = [
"0.0.0.0/0",
]
security_groups = [
aws_security_group.two-tier-ec2-sg.id,
]
}
ingress {
to_port = 22
protocol = "tcp"
from_port = 22
cidr_blocks = [
"10.0.0.0/16",
]
security_groups = [
aws_security_group.two-tier-ec2-sg.id,
]
}
}
# Bastion Host machine
resource "aws_instance" "two-tier-bastion-server" {
subnet_id = aws_subnet.two-tier-pub-sub-1.id
key_name = "bastion-server-key"
instance_type = "t2.micro"
ami = "ami-064eb0bee0c5402c5"
security_groups = [
aws_security_group.two-public-sg.id,
]
tags = {
Name = "two-tier-bastion-server"
}
}
# Private server machine
resource "aws_instance" "two-tier-private-instance" {
subnet_id = aws_subnet.2-tier-private-subnet.id
key_name = "private-server-key"
instance_type = "t2.micro"
ami = "ami-064eb0bee0c5402c5"
security_groups = [
aws_security_group.two-private-sg.id,
]
tags = {
Name = "two-tier-private-instance"
}
}
I hope this blog provides you with a clearer understanding of the step-by-step process for creating a 2-tier architecture on AWS using the powerful Infrastructure as Code (IaC) tool, Terraform. Thank you!
Feel free to contact me:
→ https://www.linkedin.com/in/saqib-ullah-siddiqui/
→ saqibullah@gmail.com