Part 1: Deploying a Secure Full-Stack Application on AWS EC2 with Docker and Nginx
Deploying a full-stack application could be overwhelming. In this regard, it involves many steps and configurations to achieve seamless functioning. Setting up a stable and secure environment requires meticulous planning and execution. This section will walk you through how to set up such an environment, including the essential steps: launching an EC2 Instance, setting security settings, automating scripts and connecting to an EC2 instance.
Setting up the proper environment is vital to stable and secure deployment processes. The tools we recommend, such as AWS EC2, Docker, and automated scripts, are designed to make your job easier. They streamline the setup process, reduce potential errors, and enhance security measures. Following our step-by-step guide, you can quickly deploy a full-stack Application, confident in the robust and efficient setup you've created for your Application.
Prerequisites
Before you begin, make sure you have the following:
AWS account: You will need this to create and manage your EC2 instances.
Domain Name: Used to route traffic to your Application.
Docker: A basic understanding of Docker and Docker Compose for managing your application containers.
Nginx: Familiarity with Nginx is necessary to set up your web server.
Linux command line: command-line instructions to configure your environment and deploy your Application.
Step 1: Setting Up the EC2 Instance
Launching an EC2 Instance
Log in to your AWS account and search for EC2. Click on it and select the launch instance button to start setting up an instance configuration. Follow the instructions below to ensure your instance is configured correctly for your deployment.
Select the Ubuntu 22.04 LTS AMI:
Give your EC2 a name of your choice, but I am naming mine Techdoc-backend.
Choose "Ubuntu" under Server 22.04 LTS from the list of available AMIs and ensure it is "Canonical, Ubuntu, 24.04 LTS, amd64 noble image build." Every other setting remains the default.
Choose the Instance Type and set the Key Pair:
Since our Application contains a database and other configurations, we will select the t3.small instance type to ensure enough CPU and Memory are available for our workloads.
You need to create a new key pair to connect to your EC2 via the CLI. It's important because you might want to transfer files from your local machine to your EC2 servers. Create and download the key pair.
Configuring Network settings
To ensure the Application properly connects to our EC2, it is essential to set up the necessary inbound rules by enabling the port used by our Applications and configuring the database port.
Setting Up Inbound Rules:
Select the Edit button in the Network section, scroll down, and select "Add Security group rule."
In the Inbound Security Group Rules section, For Type, select HTTP; for Source, select "Anywhere" This allows HTTP traffic to our EC2. Repeat these steps for the following ports below.
SSH: Port 22, Source: Anywhere (0.0.0.0/0) - This allows SSH access.
HTTP: Port 80, Source: Anywhere (0.0.0.0/0) - This allows HTTP traffic.
HTTPS: Port 443, Source: Anywhere (0.0.0.0/0) - This allows HTTPS traffic.
Custom TCP: Port 8000, Source: Anywhere(0.0.0.0/0) - Our Application uses this port to connect to our Express.js server. Configure yours and use your port for your Application.
Custom TCP: Port 27017, Source: Anywhere(0.0.0.0/0) - This port allows us to connect to MongoDB in the EC2 instance because we need remote access. If Your MongoDB runs on another server, you may not need this port open.
Custom TCP: Port 3000, Source: Anywhere(0.0.0.0/0) - This allow us to connect t our frontend Application. If you do not need this port for production, you can leave it closed.
Configure the storage:
Change from 8 to 30 to ensure our Application has enough storage to install the necessary software from our user script, which we will configure next.
Step 2: Configuring the Instance with a User Data Script
Using User Data Script
User data scripts are bash scripts that are powerful tools for automating the setup of your EC2 instance upon launch. They can install software, configure services, and set up your environment without manual intervention.
Script to Automate Installation and Configuration:
To configure your instance with a user data script, follow these steps:
Click on the "Advanced Details":
Scroll down to the "User Data" section.
Under "Metadata version," select "V1 and V2 (token optional)".
Copy and paste the bash script below into the User Data section:
#!/bin/bash # Update the package index sudo apt update -y sudo apt upgrade -y # Install Docker sudo apt install docker.io -y sudo systemctl start docker sudo systemctl enable docker sudo usermod -aG docker ubuntu # Install Docker Compose sudo curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose sudo chmod +x /usr/local/bin/docker-compose # Install Git sudo apt install git -y # Install Nginx sudo apt install nginx -y sudo systemctl start nginx sudo systemctl enable nginx # Install Certbot sudo apt install certbot python3-certbot-nginx -y # Create Docker network sudo docker network create app-network # Create the project directory # Change to your own folder directory [techdoc-backend] mkdir -p /home/ubuntu/techdoc-backend # Change ownership of the project directory to ubuntu sudo chown ubuntu:ubuntu /home/ubuntu/techdoc-backend # Clone the repository into the project directory as ubuntu # Please Change to your own github repo link sudo -u ubuntu git clone https://github.com/lokytech5/techdoc-backend.git /home/ubuntu/techdoc-backend # Navigate to the project directory cd /home/ubuntu/techdoc-backend # Ensure correct permissions for the project directory sudo chown -R ubuntu:ubuntu /home/ubuntu/techdoc-backend # Create the .env file in the project directory # Add Application environment variable cat <<EOF > /home/ubuntu/techdoc-backend/.env MONGO_URI=mongodb://root:example@tutihair_db:27017/tutiEcommerceDB?authSource=admin # MONGO_LOCAL_DB_SETUP=mongodb://127.0.0.1:27017/tutiEcommerceDB EOF # Ensure correct permissions and ownership for the .env file sudo chown ubuntu:ubuntu /home/ubuntu/techdoc-backend/.env # Start the Docker Compose services sudo -u ubuntu docker-compose -f /home/ubuntu/techdoc-backend/docker-compose.yml up -d # Print completion message echo "Docker installation complete, and Application started" # Prompt user to log out and log back in for Docker group membership to take effect echo "Please log out and log back in for Docker group membership to take effect." # Set up Certbot (It can't be automated becasue it requires user interaction) # You must manually complete this step after the instance is up echo "Run 'sudo certbot --nginx' to set up SSL after the instance is running."
Explanation:
sudo apt update -y
: Updates the package list to get the latest versions of packages and their dependencies.sudo apt upgrade -y
: Upgrades all the installed packages to their latest versions.sudo apt install
docker.io
-y
: To install Docker.sudo systemctl start docker
: Starts the Docker service.sudo systemctl enable docker
: Enables Docker to start on boot.sudo usermod -aG docker ubuntu
: Adds theubuntu
user to the Docker group.sudo curl -L "
[https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname
](github.com/docker/compose/releases/download..-s)-$(uname -m)" -o /usr/local/bin/docker-compose
: To Download Docker Compose.sudo chmod +x /usr/local/bin/docker-compose
: Makes Docker Compose executable.sudo apt install git -y
: Installs Git for cloning the repository.sudo apt install nginx -y
: Installs Nginx.sudo systemctl start nginx
: Starts the Nginx service.sudo systemctl enable nginx
: Enables Nginx to start on boot.sudo apt install certbot python3-certbot-nginx -y
: Installs Certbot for SSL certificates.sudo docker network create app-network
: Creates a Docker network namedapp-network
.mkdir -p /home/ubuntu/techdoc-backend
: Creates the project directory.sudo chown ubuntu:ubuntu /home/ubuntu/techdoc-backend
: Changes the ownership of the directory to theubuntu
user.sudo -u ubuntu git clone
https://github.com/lokytech5/techdoc-backend.git
/home/ubuntu/techdoc-backend
: Clones the repository into the project directory as theubuntu
user.cat <<EOF > /home/ubuntu/techdoc-backend/.env ... EOF
: Creates the.env
file containing the essential environment variables forsudo chown ubuntu:ubuntu /home/ubuntu/techdoc-backend/.env
: Ensures the.env
file has the correct permissions and ownership.sudo -u ubuntu docker-compose -f /home/ubuntu/techdoc-backend/docker-compose.yml up -d
: Starts the Docker Compose services.echo "Docker installation complete, and application started"
: Prints a completion message.echo "Please log out and log back in for Docker group membership to take effect."
: Prompts the user to log out and back in for Docker group membership to take effect.echo "Run 'sudo certbot --nginx' to set up SSL after the instance is running."
: Instruct the user to complete the SSL setup with Certbot manually.
Step 3: Connecting to the EC2 Instance
Connecting to an EC2 instance is using the instance key you downloaded earlier and installing the AWS CLI on your local machine or via the AWS console. We will use the AWS console, which is quick and easy.
Connecting to the EC2 Instance
Using the AWS Console:
Navigate to the EC2 Dashboard.
Select the instance you launched.
Click on the "Connect" button.
Choose the "EC2 Instance Connect" option and click "Connect".
Verifying the Setup:
Verify Docker, Docker Compose Installation and Check Nginx Status:
Once connected, run the following command to check if Docker and Docker Compose are installed and running. Use the command below to confirm if our Nginx is working as expected.
docker --version docker-compose --version sudo systemctl status nginx
Conclusion
In this part, we have explored the essential steps to set up your environment for full-stack deployment. By automating the installation and configuration process with a user data script, we ensure reproducibility and efficiency, making your deployment process smoother and more reliable.
By setting up a secure EC2 instance and configuring it with the necessary software and services, you lay a strong foundation for your deployment. Automation saves time and reduces human error, creating a more robust and consistent deployment environment.