You are currently viewing How to Deploy a FastAPI Application on a VPS with Nginx
How to Deploy a FastAPI Application on a VPS with Nginx

How to Deploy a FastAPI Application on a VPS with Nginx

FastAPI is a powerful and modern web framework for building APIs with Python. In this guide, we’ll walk you through how to Deploy a FastAPI Application on a VPS using Nginx as a reverse proxy. We’ll also create a systemd service to manage the application, configure a domain name,and install SSL. By the end of this guide, your FastAPI application will be ready for production use.

Prerequisites

Confirm the following before begining

  1. A VPS with a Linux-based operating system (e.g., Ubuntu 20.04 or later).
  2. A registered domain name, pointing to your VPS’s IP address (optional but recommended).
  3. Python 3.7 or later installed on your VPS.

Note: The following is the setup used for this article and may be different in your case. Taken note of the setup so you can setup your systemd Service accordingly.

Working Directory: /home/ubuntu/dtechnologies.co.ke

Virtualenv Directory: /home/ubuntu/dtechnologies.co.ke/venv

Command to run my FastAPI app locally: uvicorn wsgi:app –host 0.0.0.0 –port 8000

Step 1: Set Up the FastAPI Application

Install Python and pip

Update your package repository and install python and pip.

sudo apt update -y
sudo apt install python3 python3-pip python3-venv -y

Create a Virtual Environment

Create a folder for your project and Set up a virtual environment for package management. Adjust the information used where necessary.

mkdir -p /home/ubuntu/dtechnologies.co.ke
cd /home/ubuntu/dtechnologies.co.ke
python3 -m venv venv
source venv/bin/activate

Upload your website files

Use any convenient method to get your website files to the server. Available options are SCP method, cloning a github repository, rsync etc.

#Use of scp
scp file-name.zip server-username@server-IP:/location-to-upload/
#Clone from a github repository
git clone https://github.com/danielnjama/fastapi-sample.git

Install dependecies

It is expected that the project has the requirements.txt file containing all required dependencies. Use the method below to install, otherwise install the dependencies one by one.

pip install -r requirements.txt

Step 2: Set Up systemd Service for FastAPI

Create a Service File: Create a systemd service file for your FastAPI application. This will be registered as a service and will be used to manage (start,stop,reload, enable) the application.

sudo nano /etc/systemd/system/fastapi.service

Add the following: Replace the workdirectory and the Execstart , and user with the right information for your case.

[Unit]
Description=FastAPI Application
After=network.target

[Service]
User=www-data
Group=www-data
WorkingDirectory=/home/ubuntu/dtechnologies.co.ke
ExecStart=/home/ubuntu/dtechnologies.co.ke/venv/bin/uvicorn wsgi:app --host 0.0.0.0 --port 8000
Restart=always

[Install]
WantedBy=multi-user.target

Reload systemd and Enable the Service

Reload the systemd configuration for the changes done to take effect.

sudo systemctl daemon-reload

Start, Enable and verify the service

sudo systemctl start fastapi
sudo systemctl enable fastapi
sudo systemctl status fastapi

Change permissions/Ownershiop

You might be faced with permission related errors depending with the user you are using to navigate your system. Set your work directory to be the active user apart from the root. If you are using the root user for the setup, this may not apply to you.

# Change ownership of the application directory to the www-data user and group.
# This ensures the web server (e.g., Nginx, running as www-data) has the necessary permissions 
# to access and serve files from this directory.
sudo chown -R www-data:www-data /home/ubuntu/dtechnologies.co.ke

# Set directory permissions to 755:
# - Owner (www-data) gets read, write, and execute (7).
# - Group and others get read and execute (5).
# This allows the web server to read files and execute scripts if needed while maintaining security.
sudo chmod 755 /home/ubuntu/dtechnologies.co.ke

# Add the www-data user to the ubuntu group as a supplementary group.
# This allows the web server (www-data) to access files and resources that belong to the ubuntu user, 
# which is useful when working with shared directories, logs, or socket files.
sudo usermod -aG ubuntu www-data

Step 3: Set Up Nginx as a Reverse Proxy

Install Nginx: Install nginx webserver in your VPS.

sudo apt install nginx -y

Configure Nginx: Create a new nginx configuration file for your FastApi application.

sudo nano /etc/nginx/sites-available/fastapi

Add the following content and adjust as needed.

server {
    listen 80;
    server_name your-domain.com www.your-domain.com; # Replace with your domain name or VPS IP

    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;
    }
}

Enable the Configuration: Create a symbolic link to enable the configuration.

sudo ln -s /etc/nginx/sites-available/fastapi /etc/nginx/sites-enabled/

Test the configuration for errors and restart nginx:

sudo nginx -t
sudo systemctl restart nginx

Redirect IP traffic to the domain name

You may want to prevent access of your application on IP. In that case, you can redirect that traffic to your domain name.

#Update the code to match the following
sudo nano /etc/nginx/sites-available/fastapi

Add the following block of configuration: Ensure to remove the IP address in the servername of the previous block with the domain name.

# Redirect traffic from the server's public IP to the domain
server {
    listen 80;
    server_name your-server-ip;

    return 301 http://yourdomain.com$request_uri;
}

Step 4: Configure MySQL Database(Optional)

If your fastAPI requires connection to a database, follow the following steps to configure a database.

Install MySQL on Your: run the following commands to install mysql server

sudo apt update
sudo apt install mysql-server -y

Log in to MySQL and Create a Database

Access your mysql server and create the required resources.

sudo mysql -u root -p   #incase you setup the username and password(usually not the case. Use the following method to access mysql)
sudo mysql

Create the database credentials:

CREATE DATABASE your_database_name;
CREATE USER 'myuser'@'localhost' identified by 'mypassword';
GRANT ALL PRIVILEGES ON fastapidb.* TO 'myuser'@'localhost';
FLUSH PRIVILEGES;

Ensure the database connection dependancies are installed.

pip install fastapi uvicorn sqlalchemy pymysql

Finally, ensure that the database name, username and the password are well updated in your code.

Testing

There are a number of ways to test if endpoints are reachable. This can be done on Postman, on browser, or on terminal, etc. To test on terminal:

#Get All:
curl http://IP-or-Domain-name/items
#Get One:
curl http://IP-or-Domain-name/items
#POST: 
curl -X POST "http://IP-or-Domain-name/items" -H "Content-Type: application/json"      -d '{"id":12,"name": "Sample Item", "description": "This is a test item"}'

Step 5: Add SSL

To secure your application, you can use Let’s Encrypt to enable HTTPS. Install Certbot and generate an SSL certificate: Run the following commands and follow the promts

sudo apt install certbot python3-certbot-nginx -y
sudo certbot --nginx -d your-domain.com -d www.your-domain.com

Verify the Deployment: verify your deployment by visiting your API urls and trying to the various actions that have been defined, eg GET, POST, DELETE, PUT etc. If browser testing is restricted, use Postman for testing. Once confirmed, the APIs are ready for consumption.

Make a donation to support us


Web Hosting and email hosting Packages


For web development services, SEO services, Digital marketing strategies, website set up services, web hosting and domain registration; contact Dynamic Technologies.


Related Articles: