How to Deploy Strapi (or Any Node.js App) on a VPS with PostgreSQL, Nginx & PM2

Deploy Strapi with PostgreSQL or Any Node.js App on a VPS
Deploying a Node.js application — such as Strapi, Express, or any other backend — on a VPS can be straightforward if done correctly. Follow these detailed steps to set up your server, database, reverse proxy, and process manager.
1. Update Package Manager
Update your system to ensure you have the latest packages and security patches:
sudo apt update
sudo apt upgrade
apt update— refreshes available package listapt upgrade— installs new versions of existing packages
2. Install Git and GitHub CLI
sudo apt install git gh
- Git — version control system
- GitHub CLI (gh) — interact with GitHub directly from the terminal
3. Login to GitHub
gh auth login
Authenticate using your GitHub token. Create a token from: GitHub → Settings → Developer Settings → Tokens.
4. Create a Folder for Your Project
mkdir lib
cd lib
5. Clone Your Project
git clone <project-http>
Replace <project-http> with your repository's HTTPS clone URL.
6. Install NVM (Node Version Manager)
Install the latest version from NVM’s GitHub:
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.7/install.sh | bash
7. Configure NVM in Your Shell
Add NVM to your shell config:
export NVM_DIR="$([ -z "${XDG_CONFIG_HOME-}" ] && printf %s "${HOME}/.nvm" || printf %s "${XDG_CONFIG_HOME}/nvm")"
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"
Reload your shell:
source ~/.bashrc
8. Install Node.js
nvm install <version>
Example:
nvm install 20.15.1
9. Install PostgreSQL (Required for Strapi)
sudo apt install postgresql postgresql-contrib
10. Configure PostgreSQL
Start service:
sudo systemctl start postgresql.service
Switch to postgres user:
sudo -i -u postgres
psql
Inside psql terminal:
CREATE USER username WITH PASSWORD 'password';
ALTER USER username WITH SUPERUSER;
CREATE DATABASE database_name;
Exit:
\q
exit
11. Add a .env File
Inside your project:
nano .env
Add environment variables such as:
DATABASE_HOST=localhost
DATABASE_PORT=5432
DATABASE_USERNAME=username
DATABASE_PASSWORD=password
DATABASE_NAME=database_name
12. Test Your Project
Install dependencies:
npm install
Run the dev server:
npm run dev
13. Install PM2 (Process Manager)
npm install -g pm2
14. Build and Start the Project
npm run build
pm2 start npm --name "strapi" -- run start
15. Auto-Start PM2 on Boot
pm2 save
pm2 startup
16. Install Nginx (Reverse Proxy)
sudo apt install nginx
17. Configure Nginx
Create config file:
sudo nano /etc/nginx/sites-available/strapi
Add:
server {
listen 80;
server_name use_domain_name_or_ip_here;
location / {
proxy_pass http://localhost:1337;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
18. Enable Nginx Config
sudo ln -s /etc/nginx/sites-available/strapi /etc/nginx/sites-enabled/
sudo rm /etc/nginx/sites-enabled/default
19. Test Nginx Configuration
sudo nginx -t
20. Restart Nginx
sudo systemctl restart nginx
21. Increase File Upload Limit (Optional)
sudo nano /etc/nginx/nginx.conf
Inside the http block:
client_max_body_size 100M;
22. Allow Firewall Traffic (UFW)
Allow HTTP + HTTPS:
sudo ufw allow 'Nginx Full'
OR allow individually:
sudo ufw allow 'Nginx HTTP'
sudo ufw allow 'Nginx HTTPS'
Check firewall status:
sudo ufw status
Conclusion
By following these steps, you can deploy Strapi or any other Node.js application on a VPS with:
- PostgreSQL database
- PM2 for process management
- Nginx as a reverse proxy
- Firewall rules for security
This setup ensures your app runs efficiently, securely, and automatically starts on system reboot.
Found this article helpful?