Deploying FastAPI applications to production on a VPS requires careful configuration. This step-by-step guide will walk you through the entire process.
Prerequisites
- A VPS with Ubuntu 20.04 or later
- Domain name (optional but recommended)
- Basic knowledge of Linux commands
Step 1: Server Setup
Update System
sudo apt update
sudo apt upgrade -y
Install Python and Dependencies
sudo apt install python3.9 python3-pip python3-venv nginx supervisor -y
Step 2: Create Application Directory
mkdir -p /var/www/myapp
cd /var/www/myapp
Create Virtual Environment
python3 -m venv venv
source venv/bin/activate
Step 3: Deploy Your Application
Install Dependencies
pip install fastapi uvicorn[standard] gunicorn
Create Application File
# main.py
from fastapi import FastAPI
app = FastAPI()
@app.get("/")
def read_root():
return {"Hello": "World"}
@app.get("/health")
def health_check():
return {"status": "healthy"}
Step 4: Configure Gunicorn
Create gunicorn_config.py:
# gunicorn_config.py
bind = "127.0.0.1:8000"
workers = 4
worker_class = "uvicorn.workers.UvicornWorker"
timeout = 120
keepalive = 5
Step 5: Setup Supervisor
Create /etc/supervisor/conf.d/myapp.conf:
[program:myapp]
command=/var/www/myapp/venv/bin/gunicorn -c /var/www/myapp/gunicorn_config.py main:app
directory=/var/www/myapp
user=www-data
autostart=true
autorestart=true
redirect_stderr=true
stdout_logfile=/var/log/myapp.log
Start the service:
sudo supervisorctl reread
sudo supervisorctl update
sudo supervisorctl start myapp
Step 6: Configure Nginx
Create /etc/nginx/sites-available/myapp:
server {
listen 80;
server_name yourdomain.com;
location / {
proxy_pass http://127.0.0.1:8000;
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;
}
}
Enable the site:
sudo ln -s /etc/nginx/sites-available/myapp /etc/nginx/sites-enabled/
sudo nginx -t
sudo systemctl restart nginx
Step 7: Setup SSL with Let’s Encrypt
sudo apt install certbot python3-certbot-nginx -y
sudo certbot --nginx -d yourdomain.com
Step 8: Security Hardening
Firewall Configuration
sudo ufw allow 22
sudo ufw allow 80
sudo ufw allow 443
sudo ufw enable
Environment Variables
Create .env file:
# .env
DATABASE_URL=postgresql://user:pass@localhost/dbname
SECRET_KEY=your-secret-key-here
Load in application:
from dotenv import load_dotenv
import os
load_dotenv()
DATABASE_URL = os.getenv("DATABASE_URL")
SECRET_KEY = os.getenv("SECRET_KEY")
Step 9: Monitoring and Logging
Setup Log Rotation
Create /etc/logrotate.d/myapp:
/var/log/myapp.log {
daily
rotate 14
compress
delaycompress
notifempty
create 0640 www-data www-data
sharedscripts
}
Health Check Endpoint
Already included in the application, monitor with:
curl http://localhost:8000/health
Step 10: Performance Optimization
Increase Worker Processes
Adjust in gunicorn_config.py:
workers = (2 * CPU_COUNT) + 1
Enable Caching
from fastapi_cache import FastAPICache
from fastapi_cache.backends.redis import RedisBackend
@app.on_event("startup")
async def startup():
redis = aioredis.from_url("redis://localhost")
FastAPICache.init(RedisBackend(redis), prefix="myapp-cache")
Troubleshooting
Check Application Logs
sudo tail -f /var/log/myapp.log
Check Supervisor Status
sudo supervisorctl status myapp
Restart Services
sudo supervisorctl restart myapp
sudo systemctl restart nginx
Conclusion
Following these steps will give you a production-ready FastAPI deployment on a VPS. Remember to:
- Keep your dependencies updated
- Monitor application logs regularly
- Set up automated backups
- Use environment variables for secrets
- Enable SSL/TLS encryption
- Configure proper firewall rules
Your FastAPI application is now running in production!