How to install and configure Django with Postgres, Nginx and Gunicorn

A few days ago, I found a great artificial intelligence learning website, which is easy to understand and humorous. I can’t help sharing it with you. Click to jump to the website.

Prerequisites


This tutorial assumes that you have set up your droplet (VPS) on Debian 7 or a similar Linux distribution such as Ubuntu. If you haven’t already done so, follow the tutorial for setting up a droplet here.

For convenience, I have divided this tutorial into two parts. The first part (steps 1-6) only covers the installation process. If you’re a more advanced Django user and just need help installing things, you can stop at step 6. If you already have everything installed and just want to know how to configure everything, you can skip to step 7. If you feel you need help from start to finish, then go through the steps in order and you should not have a problem. Let’s get started!

Step 1: Update the package


Before we do anything, we need to make sure that all the packages installed on our VPS are up to date. To do this, connect to your VPS via SSH and run the following command:

sudo apt-get update
sudo apt-get upgrade 

The first command downloads any updates to packages managed through apt-get. The second command installs the downloaded update. After running the above command, you may be prompted whether to install the update if one is available for installation. If this happens, simply enter “y” and press “enter” when prompted.

Step 2: Install and create Virtualenv


Installing virtualenv is simple. Simply run the following command:

sudo apt-get install python-virtualenv 

That’s it! Now let’s create our virtualenv so we can install Django and other Python packages in it:

sudo virtualenv /opt/myenv 

Notice that a new directory named “myenv” is created in the “/opt” directory. This is where our virtualenv is located. Be sure to replace “/opt/myenv” with the path where you want to install virtualenv. I usually put my env in/opt, but this is purely a personal preference. Some people create a directory called “webapps” at the root of their VPS. Choose the method that makes the most sense to you.

Step 3: Install Django


Now we need to activate our virtualenv so that when we install Python packages, they install into our virtualenv. This is how to activate your virtualenv:

source /opt/myenv/bin/activate 

You should now see ” (myenv)” appended to the beginning of your terminal prompt. This will help you know when your virtualenv is active and which virtualenv is active if you have more than one on your VPS.

We can now install Django while your virtualenv is active. To do this, we’ll use pip, a Python package manager similar to easy \ _ install. Here is the command you will run:

pip install django 

Now you have Django installed in your virtualenv! Now let’s start our database server.

Step 4: Install PostgreSQL


Most Django users prefer to use PostgreSQL as their database server. It’s more powerful than MySQL, and Django ORM is more compatible with PostgreSQL than MySQL, MSSQL, or other databases.

Since we don’t need our virtualenv to be active, run the following command to deactivate:

deactivate 

This will always deactivate any virtualenv that is currently active. Now we need to install the dependencies of PostgreSQL for use with Django, using the following command:

sudo apt-get install libpq-dev python-dev 

Now that you’re done, you can install PostgreSQL like this:

sudo apt-get install postgresql postgresql-contrib 

PostgreSQL is now installed on your computer and ready to go.

Step 5: Install NGINX


NGINX is a very fast and lightweight Web server. We will use this to serve static files for our Django application. Just run the following command to install it:

sudo apt-get install nginx 

Remember, you still need to start NGINX, but we’ll cover that when we start configuring our VPS.

Step 6: Install Gunicorn


Gunicorn is a very powerful Python WSGI HTTP server. Since it is a Python package, we need to first activate our virtualenv to install it. Here’s how we do it:

source /opt/myenv/bin/activate 

Make sure you see the added “myenv” at the beginning of the terminal prompt. Now that your virtualenv is active, run the following command:

pip install gunicorn 

Gunicorn is now installed in your virtualenv.

If you just want to install everything, feel free to stop here. Otherwise, read on for instructions on how to configure everything to make your application accessible to others on the network.

Step 7: Configure PostgreSQL


Let’s start by configuring PostgreSQL. With PostgreSQL, we need to create a database, create a user, and grant the user we created access to the database we created. First run the following command:

sudo su - postgres

Your terminal prompt should now read “postgres @ yourserver”. If this is the case, run the following command to create your database:

createdb mydb

Your database is now created and has the name “mydb” if you did not change the command. You can name your database as you like. Now create your database user using the following command:

createuser -P

You will now be presented with a series of six prompts. The first one will ask you to enter the name of the new user. Use any name you want. The next two prompts ask you to enter the new user’s password and to confirm the password. For the last 3 prompts, just enter “n” and press “enter”. This is just to make sure that your new user only has access to what you give it access to, and nothing else. Now activate the PostgreSQL command line interface like this:

psql

Finally, grant this new user access to your new database using the following command:

GRANT ALL PRIVILEGES ON DATABASE mydb TO myuser;

Now you have a PostgreSQL database and a user to access it. Now we can install Django and set it up to use our new database.

Step 8: Create a Django project


To proceed further, we need a Django project to test. This will allow us to see if what we are doing is working. Change the directory to your virtual environment directory (in my case/opt/myenv) like this:

cd /opt/myenv

Now make sure your virtual environment is active. If you’re not sure, just run the following command to make sure you’re activated:

source /opt/myenv/bin/activate

Now that your virtual environment is activated, run the following command to start a new Django project:

django-admin.py startproject myproject

You should see a new directory named “myproject” in your virtual environment directory. This is where our new Django project files are located.

To enable Django to communicate with our database, we need to install a backend for PostgreSQL. Make sure your virtual environment is active and run the following command to do so:

pip install psycopg2

Change the directory to the new “myproject” directory, and then go to its subdirectory, also called “myproject”, like this:

cd /opt/myenv/myproject/myproject

Edit the settings. Py file using the editor of your choice:

nano settings.py

Locate the database settings and edit them as follows:

 DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.postgresql_psycopg2', # Add 'postgresql_psycopg2', 'mysql', 'sqlite3' or 'oracle'.
            'NAME': 'mydb',                      # Or path to database file if using sqlite3.
            # The following settings are not used with sqlite3:
            'USER': 'myuser',
            'PASSWORD': 'password',
            'HOST': 'localhost',                      # Empty for localhost through domain sockets or           '127.0.0.1' for localhost through TCP.
            'PORT': '',                      # Set to empty string for default.
        }
    } 

Save and exit the file. Now move up one directory so that you are in your main Django project directory (/opt/myenv/myproject).

cd /opt/myenv/myproject

If you have not already activated your virtual environment, use the following command to do so:

source /opt/myenv/bin/activate

With your virtual environment active, run the following command so Django can add its initial configuration and other tables to your database:

python manage.py syncdb

You should see some output describing which tables are installed, and then you will be prompted if you want to create a superuser. This is optional, depending on whether you will be using Django’s authentication system or the Django administration interface.

Step 9: Configure Gunicorn


Gunicorn’s configuration is very specific to the needs of your application. I’ll briefly explain how to run Gunicorn here with some different settings.

First, let’s just cover running Gunicorn with the default settings. Here are the commands to run only the default Gunicorn:

gunicorn_django --bind yourdomainorip.com:8001

Be sure to replace “yourdomainorip. Com” “with your domain name or the IP address of your VPS. Now go to your web browser, visit yourdomainorip. Com: 8001, and see what you get. You should see Django’s welcome screen.

However, if you look closely at the output of the above command, you’ll notice that only one Gunicorn worker process has started. What if you launch a large-scale application on a large VPS? Don’t worry! We just need to modify the command slightly, like this:

gunicorn_django --workers=3 --bind yourdomainorip.com:8001

You will now notice that 3 worker processes are started instead of just 1. You can change this number as needed.

Since we ran the command to start Gunicorn as root, Gunicorn is now running as root. If you do not want this, we can modify the above command slightly to accommodate:

gunicorn_django --workers=3 --user=nobody --bind yourdomainorip.com:8001

If you want to set more options for Gunicorn, it’s a good idea to set up a configuration file to call when you run Gunicorn. This will result in a shorter and easier to read/configure Gunicorn command.

You can put gunicorn’s profile anywhere you like. For simplicity, we put it in our virtual environment directory. Navigate to your virtual environment directory like this:

cd /opt/myenv

Now open your configuration file using your favorite editor (nano is used in the example below):

sudo nano gunicorn_config.py

Add the following to the file:

 command = '/opt/myenv/bin/gunicorn'
    pythonpath = '/opt/myenv/myproject'
    bind = '127.0.0.1:8001'
    workers = 3
    user = nobody 

Save and exit the file. What these options do is set the path to the Gunicorn binary, add your project directory to your Python path, bind the domain and port to Gunicorn, set the number of Gunicorn worker processes, and set which user Gunicorn will run as.

To run the server, we need a slightly longer command this time. Enter the following command at your prompt:

/opt/myenv/bin/gunicorn -c /opt/myenv/gunicorn_config.py myproject.wsgi

You’ll notice that in the above command, we passed the “-C” flag. This tells gunicorn that we have a configuration file to use, which we passed after the “-C” flag. Finally, we passed a Python dot notation reference to our WSGI file so that Gunicorn knows where our WSGI file is.

Running Gunicorn this way requires you to run Gunicorn in your screen session (if you’re familiar with using screen), Or press “ctrl + Z” and enter “BG” and “enter” immediately after running Gunicorn to put the process in the background so that it continues to run after the current session is closed. This also brings up the problem that if your VPS gets rebooted or crashes for some reason, you need to manually boot or reboot Gunicorn. To solve this problem, most people use supervisord to manage Gunicorn and start/restart it as needed. Installing and configuring supervisord is covered in another article, which can be found here.

Finally, this is by no means an exhaustive list of configuration options for Gunicorn. Please read the Gunicorn documentation found on the gunicorn. Org for more information.

Step 10: Configure NGINX


Before we continue, let’s start NGINX with the following command:

sudo service nginx start

Since we are just setting up NGINX to handle static files, we need to first decide where to store the static files. Open your Django project’s settings. Py file and edit the STATIC \ _ ROOT line to look like this:

 STATIC_ROOT = "/opt/myenv/static/" 

This path can be placed anywhere you like. But for the sake of neatness, I usually put it outside the Django project folder, but inside the virtual environment directory.

Now that you have set the location for the static files, let’s configure NGINX to handle them. Open a new NGINX configuration file with the following command (you can replace “nano” with your favorite editor):

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

You can name the file anything you like, but the usual standard is to name it something relevant to the site you’re configuring. Now add the following to the file:

 server {
        server_name yourdomainorip.com;

        access_log off;

        location /static/ {
            alias /opt/myenv/static/;
        }

        location / {
                proxy_pass http://127.0.0.1:8001;
                proxy_set_header X-Forwarded-Host server_name;
                proxy_set_header X-Real-IPremote_addr;
                add_header P3P 'CP="ALL DSP COR PSAa PSDa OUR NOR ONL UNI COM NAV"';
        }
    } 

Save and exit the file. The above configuration has set up NGINX to serve whatever is requested at the yourdomainorip. Com/static/from the static directory we set up for the Django project. Anything requested at the yourdomainorip. Com will be proxied to port 8001 of localhost, which is where we tell Gunicorn to run. Other lines ensure that the requested hostname and IP address are passed to Gunicorn. Without this, the IP address of each request would become 127.0.0.1, and the hostname would simply be your VPS hostname.

Now we need to set up a symbolic link in the/etc/nginx/sites-enabled directory pointing to this configuration file. This way NGINX knows that the site is active. Change to the/etc/nginx/sites-enabled directory like this:

cd /etc/nginx/sites-enabled

Once there, run the following command:

sudo ln -s ../sites-available/myproject

This will create the symlinks we need so that NGINX knows to comply with our new profile to serve our site.

Also, remove the default nginx server block:

sudo rm default

We need to restart NGINX so it knows to look for our changes. To do this, run the following command:

sudo service nginx restart

That’s it! Now that you have Django installed and working with PostgreSQL, your application serves static content via NGINX and Gunicorn acts as your application server. If you have any questions or further suggestions, be sure to leave them in the comments section.