Introduction to Terraform: A Complete AWS Deployment Guide
TerraformAWSDevOps
Recently Published
3 min read

Introduction to Terraform: A Complete AWS Deployment Guide

In the world of modern cloud computing, managing infrastructure manually is a thing of the past. Terraform allows you to treat your infrastructure as code, making it versionable, repeatable, and scalable.

In this guide, we'll walk through a complete Terraform project that sets up a secure web server on AWS.


The Project Structure

To follow along, you'll need the following files in your project directory:

  1. provider.tf: Defines the cloud provider.
  2. variables.tf: Declares input variables.
  3. terraform.tfvars: Provides values for those variables.
  4. keypair.tf: Configures SSH access.
  5. security-group.tf: Defines firewall rules.
  6. main.tf: The core resource configuration.
  7. setup.sh: A startup script for the web server.
  8. outputs.tf: Displays important information after deployment.

1. Setting Up the Foundation

provider.tf

First, we tell Terraform to use the AWS provider and specify our target region.

provider "aws" {
  region = var.region
}

variables.tf & terraform.tfvars

Variables keep our code flexible. We define them in variables.tf and provide specific values in terraform.tfvars.

variables.tf:

variable "region" { default = "eu-north-1" }
variable "instance_type" { default = "t3.micro" }
variable "ami" { description = "AMI ID" }
variable "key_name" { default = "my-key" }

terraform.tfvars:

ami = "ami-0aaa636894689fa47"

2. Security and Access

keypair.tf

To SSH into our instance, we need a key pair. This resource uploads your local public key to AWS.

resource "aws_key_pair" "deployer" {
  key_name   = var.key_name
  public_key = file("~/.ssh/id_rsa.pub")
}

security-group.tf

We need to open ports 22 (SSH) and 80 (HTTP) to access our server.

resource "aws_security_group" "ec2_sg" {
  name        = "ec2_sg"
  description = "Allow SSH and HTTP access"

  ingress {
    from_port   = 22
    to_port     = 22
    protocol    = "tcp"
    cidr_blocks = ["0.0.0.0/0"]
  }

  ingress {
    from_port   = 80
    to_port     = 80
    protocol    = "tcp"
    cidr_blocks = ["0.0.0.0/0"]
  }

  egress {
    from_port   = 0
    to_port     = 0
    protocol    = "-1"
    cidr_blocks = ["0.0.0.0/0"]
  }
}

3. The Core Resource: EC2 Instance

main.tf

This is where everything comes together. We use the variables, the key pair, and the security group to launch our instance.

resource "aws_instance" "my_ec2" {
  ami           = var.ami
  instance_type = var.instance_type
  key_name      = aws_key_pair.deployer.key_name

  vpc_security_group_ids = [aws_security_group.ec2_sg.id]

  tags = { Name = "MyTerraformEC2" }

  user_data = file("setup.sh") # Bootstrap the server!
}

setup.sh (User Data)

This script runs automatically when the instance starts. It installs Apache and a creative website template.

#!/bin/bash
yum update -y
yum install -y httpd wget unzip
systemctl start httpd
systemctl enable httpd
cd /tmp
wget https://www.tooplate.com/zip-templates/2156_graphite_creative.zip -O creative.zip
unzip creative.zip
cp -r 2156_graphite_creative/* /var/www/html/
chown -R apache:apache /var/www/html/*
rm -rf 2156_graphite_creative creative.zip

4. Getting Results

outputs.tf

After deployment, we want to know the public IP address of our server immediately.

output "public_ip" {
  value = aws_instance.my_ec2.public_ip
}

How to Run This Project

  1. Prerequisites: Ensure you have the AWS CLI configured and an SSH key pair generated (~/.ssh/id_rsa.pub).
  2. Initialize: Run terraform init to download providers.
  3. Plan: Run terraform plan to see the proposed changes.
  4. Apply: Run terraform apply to deploy the infrastructure.

Once finished, copy the public_ip from the output, paste it into your browser, and enjoy your new website!


Conclusion

You've just deployed a full web infrastructure using Terraform! By splitting the configuration into logical files, you've created a project that is easy to read, maintain, and share.

Happy Coding!