Posted on 2025-07-07
Complete Guide to Deploying MERN Stack Project on Hostinger VPS
Deploying a MERN (MongoDB, Express.js, React, Node.js) stack application on a VPS can seem overwhelming at first, but with this comprehensive guide, even a 15-year-old can successfully set up their own production-ready web application. We'll walk through each step in detail, explaining not just what to do, but why we're doing it.
What You'll Learn
By the end of this tutorial, you'll have a fully functional MERN stack application running on Hostinger VPS with proper security, SSL certificates, and professional deployment practices123.
Why Choose Hostinger VPS?
Hostinger VPS offers an excellent balance of affordability and performance, starting at just $4.49 per month4. Unlike shared hosting, VPS provides dedicated resources including CPU, RAM, and disk space, ensuring your application runs smoothly without interference from other websites56. With features like full root access, NVMe SSD storage, and 24/7 customer support, it's perfect for hosting MERN applications78.
Step 1: Preparing Your VPS Environment
Getting Your VPS Ready
First, you'll need to purchase a VPS plan from Hostinger. Once you have your VPS details, let's connect and set it up properly.
Connecting to Your VPS
Open your terminal (Command Prompt on Windows, Terminal on Mac/Linux) and connect to your server:
bash
ssh root@your_vps_ip Replace your_vps_ip with the actual IP address provided by Hostinger49.
Updating Your System
Always start with a fresh, updated system:
bash
sudo apt update
sudo apt upgrade -y This ensures all packages are up-to-date and security patches are applied1011.
Step 2: Installing Node.js with NVM
Instead of installing Node.js directly, we'll use NVM (Node Version Manager) for better version control. This approach allows you to switch between different Node.js versions easily, which is crucial for different projects121314.
Installing NVM
bash
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.3/install.sh | bash After installation, you might see "Command 'nvm' not found". This is normal! Simply restart your terminal connection:
bash
exit Then reconnect:
bash
ssh root@your_vps_ip If it still doesn't work, manually load NVM:
bash
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" Installing Node.js
Now install the latest LTS version of Node.js:
bash
nvm install --lts Or install a specific version:
bash
nvm install < version >Installing Git
Git is essential for cloning your project repositories:
bash
sudo apt install -y git Step 3: Setting Up MongoDB (Optional)
If you're using MongoDB Atlas (cloud database), you can skip this section. However, if you want to set up MongoDB locally on your VPS, follow the MongoDB installation guide1516.
For beginners, we recommend using MongoDB Atlas as it provides automatic backups, scaling, and monitoring without the complexity of managing your own database server1516.
Step 4: Deploying Your Express.js and Node.js Backend
Setting Up Project Structure
Create a proper directory structure for your projects:
bash
mkdir /var/www
cd /var/www
mkdir myproject
cd myproject Cloning Your Backend Repository
bash
git clone https://github.com/yourusername/your-repo.git
cd your-repo/backend Installing Dependencies
bash
npm install Setting Up Environment Variables
Environment variables are crucial for keeping sensitive information secure171819. Create a .env file:
bash
nano .env Add your environment variables:
text
PORT=4000
MONGODB_URI=your_mongodb_connection_string
JWT_SECRET=your_jwt_secret
NODE_ENV=production Save and exit by pressing Ctrl + X, then Y, then Enter.Installing and Configuring PM2
PM2 is a production-grade process manager that keeps your Node.js applications running202122. It automatically restarts your app if it crashes and provides monitoring capabilities.
bash
npm install -g pm2 Start your backend application:
bash
pm2 start server.js --name project-backend Important: Replace server.js with your actual entry file (might be index.js or app.js).
Making PM2 Persistent
To ensure your application starts automatically after server reboots:
bash
pm2 save
pm2 startup The pm2 startup command will show you a command to copy and paste back into the terminal - follow those instructions2123.
Step 5: Configuring Firewall with UFW
Security is paramount when deploying applications. UFW (Uncomplicated Firewall) helps protect your server242526.
Checking Firewall Status
bash
sudo ufw status Enabling Firewall
bash
sudo ufw enable
sudo ufw allow 'OpenSSH' Allowing Your Backend Port
bash
sudo ufw allow 4000 Replace 4000 with whatever port your backend uses.
Step 6: Deploying React Frontend
Building Your React Application
Navigate to your React application directory:
bash
cd /var/www/myproject/your-repo/frontend npm install Setting Up Frontend Environment Variables
If your React app uses environment variables:
bash
nano .env Add your variables (remember, React environment variables must start with REACT_APP_):
text
REACT_APP_API_URL=http://your_vps_ip:4000
REACT_APP_ENV=production Creating Production Build
Build your React app for production272829:
bash
npm run build This creates optimized static files in a build directory2829.
Testing the Build Locally
bash
npm run preview -- --host If you can't access it externally, allow the preview port:
bash
sudo ufw allow 4173 Step 7: Installing and Configuring Nginx
Nginx acts as a reverse proxy, serving your React app and forwarding API requests to your backend303132.
Installing Nginx
bash
sudo apt install -y nginx Configuring Firewall for Nginx
bash
sudo ufw allow 'Nginx Full' Setting Up Nginx Configuration
Navigate to Nginx configuration directory:
bash
cd /etc/nginx/sites-available Remove the default configuration:
bash
cd /etc/nginx/sites-enabled/
rm default Create your custom configuration:
bash
cd /etc/nginx/sites-available
nano your-domain.conf Add this configuration:
text
server {
listen 80;
server_name your_vps_ip_or_domain;
# Serve React app
root /var/www/myproject/your-repo/frontend/build;
index index.html;
# Handle React Router location /
{
try_files $uri $uri/ /index.html;
}
# Proxy API requests to backend location /api
{
proxy_pass http://localhost:4000;
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_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_cache_bypass $http_upgrade;
}
} Enabling the Configuration
bash
ln -s /etc/nginx/sites-available/your-domain.conf /etc/nginx/sites-enabled/ Testing and Restarting Nginx
bash
sudo nginx -t
sudo systemctl restart nginx Step 8: Setting Up SSL Certificates with Let's Encrypt
SSL certificates are essential for securing your website and improving SEO rankings333435.
Installing Certbot
bash
sudo apt install snapd
sudo snap install core
sudo snap refresh core
sudo snap install --classic certbot Obtaining SSL Certificate
bash
sudo certbot --nginx -d your-domain.com Certbot will automatically modify your Nginx configuration to include SSL3637.
Setting Up Auto-Renewal
Let's Encrypt certificates expire every 90 days, but Certbot can renew them automatically:
bash
sudo certbot renew --dry-run Step 9: Managing Your Deployment
Making Changes to Your Application
For Backend Changes:
-
Make changes to your code
-
Push to your repository
-
Pull changes on the server:
bash
cd /var/www/myproject/your-repo/backend
npm install
# if package.json changed
pm2 restart project-backend For Frontend Changes:
-
Make changes to your code
-
Push to your repository
-
Update and rebuild on server:
bash
cd /var/www/myproject/your-repo/frontend
npm install
# if package.json changed
npm run build Monitoring Your Application
Checking PM2 Status
bash
pm2 status
pm2 logs
pm2 monit Checking Nginx Status
bash
sudo systemctl status nginx
sudo nginx -t Security Best Practices
-
Regular Updates: Keep your system updated with sudo apt update && sudo apt upgrade
-
Strong Passwords: Use complex passwords for all accounts
-
SSH Key Authentication: Consider setting up SSH keys instead of password authentication
-
Backup Strategy: Regularly backup your application and database
-
Monitor Logs: Check PM2 and Nginx logs regularly for any issues13839
Troubleshooting Common Issues
Application Not Starting
-
Check PM2 logs: pm2 logs
-
Verify environment variables are set correctly
-
Ensure all dependencies are installed
Cannot Access Website
-
Check if Nginx is running: sudo systemctl status nginx
-
Verify firewall rules: sudo ufw status
-
Test Nginx configuration:
sudo nginx -t
Database Connection Issues
-
Verify MongoDB connection string
-
Check if MongoDB Atlas whitelist includes your VPS IP
-
Ensure network connectivity
Performance Optimization Tips
-
Use PM2 Cluster Mode: For better performance with multiple CPU cores40
-
Enable Gzip Compression: Configure Nginx to compress responses
-
Implement Caching: Use Redis for session storage and caching
-
CDN Integration: Consider using a CDN for static assets
-
Monitor Resources: Use tools like htop to monitor server resources11
Conclusion
Congratulations! You now have a fully deployed MERN stack application running on Hostinger VPS. Your application is secure with SSL certificates, efficiently managed with PM2, and properly configured with Nginx as a reverse proxy.
This setup provides a solid foundation for production applications. As your project grows, you can scale by upgrading your VPS plan, implementing load balancing, or adding monitoring tools14142.
Remember to regularly maintain your server, monitor application performance, and keep all components updated for optimal security and performance. With this deployment, you're ready to share your MERN application with the world!