# Node.js Backend Deployment on AWS EC2

## ✅ STAR Methodology Answer:

### **S - Situation**

During my cloud learning journey, I wanted to gain hands-on experience in deploying backend services on cloud infrastructure. I chose to work with a **Node.js application** and deploy it on **AWS EC2**, simulating a real-world production backend deployment scenario.

### **T - Task**

My goal was to:

* Deploy a simple Node.js backend (REST API).
    
* Host it on an EC2 instance.
    
* Configure networking for external access.
    
* Ensure high availability and proper security.
    
* Test API endpoints using Postman. This project was aimed at understanding the end-to-end flow of cloud-based deployments and managing backend infrastructure.
    

---

### **A - Action (Detailed Step-by-Step)**

#### **1\. Setup the EC2 Instance**

* **Launched an EC2 instance** (Amazon Linux 2) via AWS Console.
    
* Chose a **t2.micro instance** under the **Free Tier**, and selected the correct **VPC and subnet**.
    
* Created a **key pair (.pem)** for SSH access.
    
* Opened **port 22 for SSH**, and **port 3000 (or 80/443)** for Node.js app in the **Security Group**.
    

#### **2\. SSH into EC2 & Setup Environment**

* Connected to EC2 using:
    
    ```plaintext
    bashCopyEditssh -i "my-key.pem" ec2-user@<Public-IP>
    ```
    
* Installed **Node.js and npm**:
    
    ```plaintext
    bashCopyEditsudo yum update -y
    curl -sL https://rpm.nodesource.com/setup_18.x | sudo bash -
    sudo yum install -y nodejs
    ```
    

#### **3\. Upload Node.js Project to EC2**

* Used **Git** to clone the repository or **SCP** to transfer files from local to EC2.
    
    ```plaintext
    bashCopyEditscp -i "my-key.pem" -r ./my-node-app ec2-user@<Public-IP>:/home/ec2-user
    ```
    

#### **4\. Install Dependencies & Start the Server**

* Navigated to the project folder:
    
    ```plaintext
    bashCopyEditcd my-node-app
    npm install
    ```
    
* Started the server:
    
    ```plaintext
    bashCopyEditnode index.js
    ```
    

#### **5\. Configure the App to Run in Background (PM2 or nohup)**

* Installed PM2:
    
    ```plaintext
    bashCopyEditnpm install -g pm2
    pm2 start index.js
    pm2 startup
    pm2 save
    ```
    

#### **6\. Security Group & Firewall Configuration**

* Ensured **inbound rules** allowed traffic to port `3000` or `80`.
    
* Verified `iptables` or `firewalld` settings (if needed).
    

#### **7\. Tested API with Postman**

* Verified public IP and tested API routes from Postman.
    
* Confirmed response status codes and payloads.
    

#### **8\. Optional: Custom Domain + Reverse Proxy (Advanced)**

* (Optional) Set up **Nginx as a reverse proxy** for production-ready setup.
    
* Linked to a **custom domain using Route 53** (optional learning addition).
    

---

### **R - Result**

* Successfully deployed a **Node.js backend on AWS EC2** with public accessibility.
    
* Gained strong understanding of:
    
    * Cloud networking
        
    * SSH & Linux setup
        
    * Security groups and firewall rules
        
    * Backend deployment lifecycle
        
* Validated API functionality using Postman.
    
* Improved confidence in handling real-world backend deployments on cloud.
    

---

## 👨‍💼 How to Explain in Interview

> “I worked on deploying a Node.js backend on AWS EC2 to simulate real-world cloud deployments. I launched and configured the EC2 instance, installed the runtime environment, transferred code, ran the server with PM2, and configured security groups for accessibility. I also tested the endpoints using Postman to ensure proper request/response handling. This gave me hands-on understanding of backend cloud deployments and taught me about cloud infrastructure, networking, and server configuration.”

---

## 💬 10 Follow-Up Questions the Interviewer Might Ask

| # | **Question** | **How to Prepare** |
| --- | --- | --- |
| 1 | Why did you choose EC2 for deployment instead of other services like Lambda or Elastic Beanstalk? | EC2 gives full control over OS, server environment, and setup — ideal for learning infrastructure management. |
| 2 | How did you ensure that your backend app keeps running even after the EC2 session ends? | By using PM2 or `nohup` to keep the process alive even after logout. |
| 3 | What are the key security practices you followed in this deployment? | Used SSH key authentication, restricted ports in Security Groups, and didn't expose unnecessary services. |
| 4 | How would you make this backend deployment production-ready? | Use Nginx as a reverse proxy, HTTPS via SSL (Let’s Encrypt), and auto-restart via PM2. Also, enable monitoring/logging. |
| 5 | How can you automate this entire deployment? | By using **Terraform** for infrastructure as code and **Jenkins/GitHub Actions** for CI/CD pipelines. |
| 6 | What’s the difference between EC2 and Lambda? | EC2 is IaaS (Infrastructure as a Service), persistent servers. Lambda is FaaS (Function as a Service), event-driven and serverless. |
| 7 | How did you test and debug errors during deployment? | Used logs (`console.log`, `pm2 logs`, `journalctl`), curl/Postman, and checked EC2 instance logs for system errors. |
| 8 | What are the limitations of using EC2 directly? | Manual setup, scaling is harder, no built-in fault tolerance unless added, and higher overhead compared to managed services. |
| 9 | How did you handle app logs and monitoring in this setup? | PM2 provides logs; for production, CloudWatch can be integrated or use file-based logs with logrotate. |
| 10 | How would you scale this application to handle more traffic? | Add a Load Balancer (ELB), configure Auto Scaling Groups, or containerize the app with Docker + ECS/EKS. |

## ✅ 5 Challenges Faced & How I Overcame Them

---

### **1\. SSH Connection Error to EC2**

**🔸Challenge:**  
When I first launched the EC2 instance, I was unable to SSH into it. The terminal kept saying "Permission denied" or "Timed out".

**🔧 Solution:**

* Ensured that the **Security Group** had **port 22 open** for inbound SSH access.
    
* Verified I was using the **correct public IP** and **.pem key file**.
    
* Changed the permissions of the key with:
    
    ```plaintext
    bashCopyEditchmod 400 my-key.pem
    ```
    
* Used the right user (`ec2-user`) in the SSH command.
    

**💡 Learning:** Importance of network rules and secure SSH practices.

---

### **2\. Node.js Not Recognized / Installation Issues**

**🔸Challenge:**  
After SSHing into the instance, the `node` and `npm` commands were not recognized.

**🔧 Solution:**

* Learned that **Amazon Linux 2** does not come with Node.js pre-installed.
    
* Installed it manually using Nodesource:
    
    ```plaintext
    bashCopyEditcurl -sL https://rpm.nodesource.com/setup_18.x | sudo bash -
    sudo yum install -y nodejs
    ```
    

**💡 Learning:** Gained hands-on experience with **package installation** and **dependency management** on Linux.

---

### **3\. Application Stopped After Logout**

**🔸Challenge:**  
The Node.js app would shut down whenever I closed the SSH terminal session.

**🔧 Solution:**

* Installed **PM2** for better process management and persistence after reboot:
    
    ```plaintext
    bashCopyEditpm2 start index.js
    pm2 save
    pm2 startup
    ```
    

**💡 Learning:** Understood the importance of **background process managers** like PM2 in real-world deployments.

---

### **4\. API Not Accessible Publicly**

**🔸Challenge:**  
Though the server was running on port 3000, I couldn’t access it from my browser or Postman using the public IP.

**🔧 Solution:**

* Realized that I needed to **add an inbound rule in the Security Group** for port 3000.
    
* Added rule:
    
    * Type: Custom TCP
        
    * Port: 3000
        
    * Source: 0.0.0.0/0 (for testing)
        
* Restarted the app and tested successfully.
    

**💡 Learning:** Learned about **AWS networking and security best practices** using security groups and firewalls.

---

### **5\. Application Not Auto-Starting After EC2 Reboot**

**🔸Challenge:**  
Every time I restarted the EC2 instance, the Node.js app wouldn’t start automatically.

**🔧 Solution:**

* Configured PM2 to generate a startup script:
    
    ```plaintext
    bashCopyEditpm2 startup
    pm2 save
    ```
    
* This ensured that PM2 would **auto-launch all apps on reboot**.
    

**💡 Learning:** Learned about **service persistence and automation** in Linux-based systems.

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1744316492545/44282195-44be-4f5a-9b71-18510080c16c.avif align="center")
