Deploy Node.js with PM2 and Nginx

By Raman Kumar

Updated on Mar 10, 2026

Deploy Node.js with PM2 and Nginx

Learn how to deploy Node.js apps using PM2 and Nginx on a Linux server.

Introduction

Running a Node.js application in production requires more than simply starting a server with node app.js. Production environments require process management, automatic restarts, logging, and a reliable web server to handle traffic efficiently.

In this guide, we deploy a Node.js application using PM2 for process management and Nginx as a reverse proxy. This approach is widely used in production environments because it ensures reliability, scalability, and efficient resource usage.

The steps below cover the complete process from server preparation to advanced production practices.

Prerequisites

Before we begin, ensure we have the following:

  • An Ubuntu 24.04 on dedicated server or KVM VPS.
  • Basic Linux Command Line Knowledge.
  • A domain name pointing A DNS record to server IP.

Learn how to deploy Node.js apps using PM2 and Nginx on a Linux server.

Prepare the Server Environment

We begin by updating the server packages. Keeping the system updated ensures compatibility and security.

sudo apt update
sudo apt upgrade -y

Install essential tools that will help with development and deployment.

sudo apt install curl git build-essential -y

These utilities are commonly required when compiling packages or cloning application repositories.

Install the Latest Node.js

The NodeSource repository provides the most stable Node.js builds for production systems.

Add the repository:

curl -fsSL https://deb.nodesource.com/setup_lts.x | sudo -E bash -

Install Node.js:

sudo apt install nodejs -y

Verify the installation:

node -v
npm -v

Using the LTS (Long Term Support) version ensures long-term stability for production workloads.

Install PM2 Process Manager

PM2 is a powerful process manager designed for Node.js applications. It keeps applications running, automatically restarts them if they crash, and provides monitoring and logging features.

Install PM2 globally:

sudo npm install pm2 -g

Verify installation:

pm2 -v

PM2 will now manage Node.js processes in the background and ensure they stay online.

Create or Deploy the Node.js Application

Applications may be deployed by cloning a repository or uploading project files to the server.

Example project setup:

mkdir my-node-app
cd my-node-app
npm init -y

Install Express:

npm install express

Create the application file.

nano app.js

Example application:

const express = require("express");
const app = express();

app.get("/", (req, res) => {
  res.send("Node.js application running with PM2 and Nginx");
});

app.listen(3000, () => {
  console.log("Server running on port 3000");
});

Start the application for testing:

node app.js

Once the application runs successfully, it is ready to be managed by PM2.

Start the Application with PM2

Instead of running the application directly with Node.js, we run it through PM2.

pm2 start app.js --name my-node-app

Check running processes:

pm2 list

View logs:

pm2 logs my-node-app

Restart the application:

pm2 restart my-node-app

Stop the application:

pm2 stop my-node-app

PM2 ensures the application continues running even if the process crashes.

Enable PM2 Auto Start on Server Boot

Production servers should automatically restore running applications after a reboot.

Generate startup configuration:

pm2 startup

Run the command displayed by PM2.

Then save the current process list:

pm2 save

Now the Node.js application will automatically restart whenever the server reboots.

Install and Configure Nginx

Nginx acts as a reverse proxy, allowing external traffic on ports 80 and 443 to be forwarded to the Node.js application running on port 3000.

Install Nginx:

sudo apt install nginx -y

Start the service:

sudo systemctl enable nginx
sudo systemctl start nginx

Verify status:

sudo systemctl status nginx

Firewall Configuration

Allow only required ports.

sudo ufw allow OpenSSH
sudo ufw allow 'Nginx Full'
sudo ufw enable

Configure Nginx Reverse Proxy

Create a new configuration file for the Node.js application.

sudo nano /etc/nginx/sites-available/node-app

Add the following configuration:

server {
    listen 80;
    server_name example.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;
    }
}

Enable the configuration:

sudo ln -s /etc/nginx/sites-available/node-app /etc/nginx/sites-enabled/

Test the configuration:

sudo nginx -t

Reload Nginx:

sudo systemctl reload nginx

Nginx will now route incoming traffic to the Node.js application.

Secure the Application with SSL (Recommended)

For production environments, HTTPS should always be enabled.

Install Certbot:

sudo apt install certbot python3-certbot-nginx -y

Generate SSL certificates:

sudo certbot --nginx -d example.com

Certbot automatically configures HTTPS and sets up renewal.

Test renewal process:

sudo certbot renew --dry-run

Enable PM2 Cluster Mode for High Traffic

PM2 supports cluster mode, which allows the application to use multiple CPU cores.

Start the application using all available CPU cores:

pm2 start app.js -i max --name my-node-app

This significantly improves performance for high-traffic applications.

Monitor Application Performance

PM2 provides real-time monitoring tools.

Open the monitoring dashboard:

pm2 monit

This view displays CPU usage, memory consumption, and application status.

For advanced monitoring environments, PM2 can integrate with external monitoring platforms.

Manage Application Logs

Logs are essential for debugging and performance monitoring.

View logs:

pm2 logs

Clear logs when necessary:

pm2 flush

Logs are stored in:

~/.pm2/logs

Maintaining clean logs helps prevent unnecessary disk usage.

Best Practices for Production Deployments

Reliable production deployments usually follow several important practices:

Environment Variables

Sensitive configuration values should not be stored in application code.

Example:

export NODE_ENV=production

PM2 can also load environment variables from configuration files.

Use a Deployment Directory

Organizing projects improves long-term maintainability.

Example structure:

/var/www/
    node-app

Zero-Downtime Reloads

PM2 allows seamless application reloads.

pm2 reload my-node-app

This restarts the application without interrupting active connections.

Final Thoughts

Deploying Node.js with PM2 and Nginx creates a stable production environment capable of handling real-world workloads. PM2 ensures applications remain online and recover automatically, while Nginx efficiently manages incoming traffic and provides an additional security layer.

By combining these tools, teams can run Node.js applications with high reliability, improved performance, and simplified operational management.

This deployment method has become a widely adopted standard across modern hosting environments and cloud platforms.