>_
EngineeringNotes
Module 04

AWS & Deployment

Moving from "Mild Hosting" to a global server.

01

Creating your First EC2

EC2 (Elastic Compute Cloud) is basically a rented Virtual Machine.

1. OS ImageChoose Ubuntu (User-friendly, huge community support).
2. Key PairCreate a new pair `.pem`. Download it immediately. You won't see it again.
3. NetworkAllow SSH traffic from "Anywhere" (0.0.0.0/0) for now.
02

The Firewall (Security Groups)

By default, AWS (and most cloud providers) blocks everything. It's a "White-list" model. If you don't explicitly allow it, it's denied.

Imagine buying a house with no doors or windows. You are safe, but you can't get in. You need to carve out holes (ports) for specific things.

The Danger of "Closed"

If you launch a server without opening Port 22 (SSH), you lock yourself out forever. You can't login to fix it.

Manual Labor

Installing Nginx isn't enough. You must manually go to AWS Console → Security Groups → Inbound Rules and add Port 80 (HTTP) and 443 (HTTPS).

Essential Ports to Open:

  • Port 22 (SSH): So YOU can control the server (Command Line).
  • Port 80 (HTTP): So USERS can view your website.
  • Port 443 (HTTPS): So traffic is encrypted (Green lock icon).
03

Server Setup & Deployment

Now that the ports are open, let's set up the environment. Choose your runtime:

1. Connect via SSH

Terminal
bash
ssh -i "key.pem" ubuntu@your-ip

2. Install Node.js (via NVM)

Use NVM to manage versions. Avoid `apt install nodejs`.

Terminal
bash
# Install NVM
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.3/install.sh | bash
source ~/.bashrc

# Install Node (LTS)
nvm install v24.13.0

3. Clone Repository

Terminal
bash
git clone https://github.com/your-username/your-repo.git
cd your-project-folder

4. Install Dependencies

Terminal
bash
npm install

5. Environment Variables

You need to create your `.env` file manually since it's not in Git.

Terminal
bash
# Open nano/vim editor
nano .env

# Paste your variables (DATABASE_URL, etc.) inside
# Press Ctrl+X, then Y, then Enter to save.

Need help with Env Vars?

See Detailed Env Guide →

6. Start Application

Terminal
bash
# For testing
npm start

# For production (runs in background)
npm install -g pm2
pm2 start index.js --name "my-app"
pm2 save

Connecting a Domain Name

Scenario: You bought sellclothes.com on GoDaddy/Namecheap. You want it to point to your new AWS server.

1. The "A Record"

Maps a Name to an IP Address.

  • Type: A
  • Name: @ (root)
  • Value: 13.234.xx.xx (Your VM Public IP)
2. The "CNAME"

Maps a Name to another Name.

  • Type: CNAME
  • Name: www / api
  • Value: sellclothes.com

The "Port Mismatch" Problem

Users will type sellclothes.com in their browser. Browsers automatically connect to Port 80 (HTTP).

But wait! Your Node app is running on Port 3000/4000 locally. Your Python app is on Port 8000.

If users go to Port 80, and your app is on Port 4000, they will see a "Site Can't Be Reached" error.

How do we bridge this gap without forcing users to type sellclothes.com:4000? Read the next section.

04

The Port 80 Problems

When users type `google.com`, the browser silently adds `:80`. It goes to Port 80 by default. So why is this hard?

Problem 1: The "Sudo" Trap

Error: EACCES: permission denied 0.0.0.0:80

Ports below 1024 are privileged. You need `sudo` (Administrator) to use them.
Risk: If you run your Node app as root, and it has a bug, the attacker gets Root Access to your entire server. Game over.

Problem 2: The "One Port Rule"

A port can only be used by ONE application at a time.

Imagine you have 2 startups on one cheap server:

  • SellClothes.com
  • SellShoes.com

Both domains want to send traffic to Port 80. But only one app can listen there.Who gets the port?

05

The Solution: Nginx Reverse Proxy

What is Nginx?

Nginx is open-source software for web serving, reverse proxying, caching, and more. It was originally designed for maximum performance and stability. Think of it as a professional traffic controller.

We need a "Reverse Proxy". Someone who stands at Port 80, takes ALL the traffic, and intelligently hands it off to your internal apps (running on 3000, 4000, etc.).

User A
(SellClothes.com)
User B
(SellShoes.com)
Port 80 →
Port 80 →
NGINX
Traffic Police
→ Port 3000
→ Port 8080
App 1
Node.js
App 2
Python
06

Practical Guide: Setting it Up

Enough theory. Here is exactly what you type in your terminal to set this up.

1. Install Nginx

Terminal
bash
sudo apt update && sudo apt install nginx -y

2. Open Config File

We need to edit the main configuration file.

Terminal
bash
sudo vi /etc/nginx/nginx.conf

3. The Minimal Config

Delete everything inside http { ... } and replace it with this to route your two shops:

/etc/nginx/nginx.conf
nginx
events {
    # Events Directive 
}

http {
    # 1. SellClothes.com -> Port 3000
    server {
        listen 80;
        server_name sellclothes.com;

        location / {
          proxy_pass http://localhost:3000;
          proxy_http_version 1.1;
          proxy_set_header Upgrade $http_upgrade;
          proxy_set_header Connection 'upgrade';
          proxy_set_header Host $host;
          proxy_cache_bypass $http_upgrade;
        }
    }

    # 2. SellShoes.com -> Port 8080
    server {
      listen 80;
      server_name sellshoes.com;

      location / {
        proxy_pass http://localhost:8080;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host $host;
        proxy_cache_bypass $http_upgrade;
      }
    }
}

4. Restart Nginx

Always reload after changing config.

Terminal
bash
sudo systemctl restart nginx
07

Secure your Application

Now that your HTTP site is live, you need to secure it with HTTPS (SSL/TLS). If you haven't done that yet, check out our guide on Certificate Management.

Go to: Certificate Management