Backend Deployment — EC2 + PM2 + nginx
The backend runs as a Node.js cluster managed by PM2 behind an nginx reverse proxy with Certbot SSL on an Ubuntu EC2 instance.
Server Details
| Setting | Value |
|---|---|
| Monorepo path | /home/ubuntu/api.intecoglogistech.com |
| PM2 process name | prod-logistech |
| Backend port | 3500 |
| Domain | api.intecoglogistech.com |
| OS | Ubuntu 22.04 |
PM2 Configuration
File: ecosystem.config.cjs (monorepo root)
module.exports = {
apps: [{
name: 'prod-logistech',
script: './apps/backend/dist/app.js',
cwd: '/home/ubuntu/api.intecoglogistech.com',
instances: 'max', // one worker per CPU core
exec_mode: 'cluster', // Node.js cluster mode for load balancing
env: {
NODE_ENV: 'production',
PORT: 3500
}
}]
}instances: 'max' automatically starts one PM2 worker per available CPU core.
Deploy Scripts
All deploy scripts are defined in the root package.json.
Production (api.intecoglogistech.com)
# Build + pm2 reload (zero-downtime, use for all regular deploys)
pnpm deploy:backend
# Build + pm2 start (use on first deploy or when ecosystem.config.cjs changes)
pnpm deploy:backend:freshInternally:
# deploy:backend
pnpm --filter @my-app/shared build \
&& pnpm --filter @my-app/backend build \
&& pm2 reload ecosystem.config.cjs --update-env
# deploy:backend:fresh
pnpm --filter @my-app/shared build \
&& pnpm --filter @my-app/backend build \
&& pm2 start ecosystem.config.cjsDevelopment (dev.intecoglogistech.com)
# Restart dev PM2 process (shared package rebuild + process reload)
pnpm deploy:dev
# Start dev PM2 process for the first time
pnpm deploy:dev:freshInternally:
# deploy:dev
pnpm --filter @my-app/shared build \
&& pnpm --filter @my-app/backend build \
&& pm2 reload ecosystem.dev.config.cjs --update-env
# deploy:dev:fresh
pnpm --filter @my-app/shared build \
&& pnpm --filter @my-app/backend build \
&& pm2 start ecosystem.dev.config.cjsThe dev PM2 config (ecosystem.dev.config.cjs) runs the compiled ./apps/backend/dist/app.js — same as production but as a single instance with NODE_ENV: 'development' and port 3501.
When to use each
| Command | When to use |
|---|---|
pnpm deploy:backend | Normal prod updates (zero-downtime cluster reload) |
pnpm deploy:backend:fresh | First prod deploy, ecosystem config changed |
pnpm deploy:dev | Normal dev updates (process reload) |
pnpm deploy:dev:fresh | First dev deploy, ecosystem.dev.config.cjs changed |
nginx Configuration
Reference file: nginx.conf (monorepo root — deploy to /etc/nginx/sites-available/)
server {
server_name app.intecoglogistech.com;
location / {
proxy_pass http://127.0.0.1:3500;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_cache_bypass $http_upgrade;
}
listen 443 ssl; # managed by Certbot
ssl_certificate /etc/letsencrypt/live/app.intecoglogistech.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/app.intecoglogistech.com/privkey.pem;
include /etc/letsencrypt/options-ssl-nginx.conf;
}
server {
if ($host = app.intecoglogistech.com) {
return 301 https://$host$request_uri;
}
listen 80;
server_name app.intecoglogistech.com;
return 404;
}SSL is managed by Certbot (Let's Encrypt). Certbot auto-renews certificates.
Dev Environment Server Details
| Setting | Value |
|---|---|
| Monorepo path | /home/ubuntu/dev.intecoglogistech.com |
| PM2 process name | dev-logistech |
| Backend port | 3501 |
| Domain | dev.intecoglogistech.com |
| Config file | ecosystem.dev.config.cjs |
The dev backend runs the compiled dist/app.js — no nodemon or babel-node. Run pnpm deploy:dev after any code change to rebuild and reload.
Useful PM2 Commands
# Check process status
pm2 status
# View live logs
pm2 logs prod-logistech
# Reload with zero downtime
pm2 reload prod-logistech
# Stop
pm2 stop prod-logistech
# Delete process from PM2 registry
pm2 delete prod-logistech
# Save current process list for auto-restart on reboot
pm2 save
pm2 startupFirst-Time Server Setup
- Install Node.js 18+, pnpm, PM2, nginx, Certbot
- Clone the repository to
/home/ubuntu/api.intecoglogistech.com(prod) or/home/ubuntu/dev.intecoglogistech.com(dev) - Create
apps/backend/.envwith all required env vars - Run:bash
pnpm install pnpm deploy:backend:fresh - Configure nginx and obtain SSL cert:bash
sudo certbot --nginx -d api.intecoglogistech.com
See docs/server-setup-ec2.md for the full step-by-step EC2 setup guide.
