This task involves deploying a 3-tier web application architecture using Terraform on AWS. The architecture consists of:
Terraform will be used to automate infrastructure provisioning.
Create a provider.tf
file to define AWS as the Terraform provider.
provider "aws" {
region = "us-east-1"
}
Define a VPC and necessary subnets in network.tf.
resource "aws_vpc" "my_vpc" {
cidr_block = "10.0.0.0/16"
}
resource "aws_subnet" "public_subnet" {
vpc_id = aws_vpc.my_vpc.id
cidr_block = "10.0.1.0/24"
map_public_ip_on_launch = true
}
resource "aws_subnet" "private_subnet" {
vpc_id = aws_vpc.my_vpc.id
cidr_block = "10.0.2.0/24"
}
Define ALB to route traffic to the app instances in alb.tf.
resource "aws_lb" "app_alb" {
name = "app-load-balancer"
internal = false
load_balancer_type = "application"
security_groups = [aws_security_group.alb_sg.id]
subnets = [aws_subnet.public_subnet.id]
}
resource "aws_lb_target_group" "app_tg" {
name = "app-target-group"
port = 80
protocol = "HTTP"
vpc_id = aws_vpc.my_vpc.id
}
resource "aws_lb_listener" "http" {
load_balancer_arn = aws_lb.app_alb.arn
port = 80
protocol = "HTTP"
default_action {
type = "forward"
target_group_arn = aws_lb_target_group.app_tg.arn
}
}
Define an EC2 instance and security group in ec2.tf.
resource "aws_security_group" "ec2_sg" {
vpc_id = aws_vpc.my_vpc.id
ingress {
from_port = 80
to_port = 80
protocol = "tcp"
cidr_blocks = ["0.0.0.0/0"]
}
}
resource "aws_instance" "app_server" {
ami = "ami-0c55b159cbfafe1f0"
instance_type = "t2.micro"
subnet_id = aws_subnet.private_subnet.id
security_groups = [aws_security_group.ec2_sg.name]
user_data = <<-EOF
#!/bin/bash
yum update -y
yum install -y httpd
systemctl start httpd
systemctl enable httpd
echo "Hello from App Tier" > /var/www/html/index.html
EOF
}
Define an Auto Scaling Group (ASG) in autoscaling.tf.
resource "aws_launch_configuration" "app_lc" {
name = "app-launch-config"
image_id = "ami-0c55b159cbfafe1f0"
instance_type = "t2.micro"
}
resource "aws_autoscaling_group" "app_asg" {
launch_configuration = aws_launch_configuration.app_lc.id
vpc_zone_identifier = [aws_subnet.private_subnet.id]
desired_capacity = 2
min_size = 1
max_size = 3
}
Define an RDS instance in rds.tf
.
resource "aws_db_instance" "app_db" {
identifier = "app-db"
allocated_storage = 20
engine = "mysql"
engine_version = "8.0"
instance_class = "db.t2.micro"
username = "admin"
password = "mypassword"
publicly_accessible = false
vpc_security_group_ids = [aws_security_group.rds_sg.id]
db_subnet_group_name = aws_db_subnet_group.db_subnet_group.name
}
Define security groups for ALB, EC2, and RDS in security.tf
.
resource "aws_security_group" "alb_sg" {
vpc_id = aws_vpc.my_vpc.id
ingress {
from_port = 80
to_port = 80
protocol = "tcp"
cidr_blocks = ["0.0.0.0/0"]
}
}
resource "aws_security_group" "rds_sg" {
vpc_id = aws_vpc.my_vpc.id
ingress {
from_port = 3306
to_port = 3306
protocol = "tcp"
security_groups = [aws_security_group.ec2_sg.id]
}
}
Define outputs in outputs.tf.
output "alb_dns_name" {
value = aws_lb.app_alb.dns_name
}
output "database_endpoint" {
value = aws_db_instance.app_db.endpoint
sensitive = true
}
Run the following Terraform commands:
terraform init
terraform plan
terraform apply -auto-approve
Copy the ALB DNS name from Terraform output and open it in a browser.
You should see Hello from App Tier
.