In this post, we will see how to very quickly set up our Django development server with a Docker + Nginx setup. Disclaimer, this article is aimed at helping you get a minimal working setup of Django and Docker quickly and as such we will not be getting into much of the how's and why's of the code. So, without further ado, let's dive in.
Prerequisite
To follow this tutorial, you should have docker and docker-compose installed locally. Head over to the official documentation for steps on how to do this.
Creating and Activating the Virtual Environment
We will use the inbuilt python venv
module for our virtual environment. To do so, execute the code below.
# for Linux
python3 -m venv venv
# for Windows
python -m venv venv
Activate the virtual environment with:
# linux
source venv/bin/activate
# windows
venv\Scripts\activate
Django Setup and Installing Dependencies
To install Django and the dependencies, run:
pip install django gunicorn
Gunicorn is a secure WSGI HTTP server that can be used to serve django applications.
Next, copy our environment-installed packages into a requirements.txt
file.
pip freeze > requirements.txt
Now, create the Django project with the command below:
django-admin startproject django_docker_compose .
Edit your settings.py
file and add a STATIC_ROOT
variable. This is where all our templates, CSS, and Javascript files will be sent to when we run python manage.py collectstatic
later on.
# settings.py
USE_TZ = True
STATIC_URL = 'static/'
STATIC_ROOT = BASE_DIR / 'static' # added
Also, update the ALLOWED_HOSTS
to include 127.0.0.1
. This is so we can access our app from the browser later.
ALLOWED_HOSTS = ['127.0.0.1']
Setting up Docker
Here, we will specify the images we want our docker containers to run. We do this using a Dockerfile
and a docker-compose
file.
Creating the Dockerfile
Create a Dockerfile
file at the root of the project. Note, Dockerfile
has no extension.
FROM python:3.8.12-slim-bullseye
ENV PYTHONUNBUFFERED 1
ARG PROJECT_DIR=/home/app/code
WORKDIR $PROJECT_DIR
RUN useradd user && chown -R user $PROJECT_DIR
RUN python -m pip install --upgrade pip
COPY requirements.txt $PROJECT_DIR
RUN pip3 install --no-cache-dir -r requirements.txt
COPY . $PROJECT_DIR
RUN python manage.py collectstatic
USER user
Creating the Docker Compose File
Create a docker-compose.yml
file at the root of the project.
version: '3.6'
services:
nginx:
build:
context: ./nginx
ports:
- 80:80
volumes:
- static_volume:/home/app/code/static
depends_on:
- web
restart: "on-failure"
web:
build:
context: .
command: sh -c "python manage.py migrate &&
gunicorn django_docker_compose.wsgi:application --bind 0.0.0.0:8000 --reload"
volumes:
- ./:/code
- static_volume:/home/app/code/static
image: web
restart: "on-failure"
volumes:
static_volume:
At a high level, we are creating two containers: web, our Django server, and Nginx, our reverse proxy server. We will serve our Django static files with Nginx.
To make this compose file work, we need to create a new directory nginx
at the root of the project and inside it, we create two new files:
Dockerfile (This will specify how we want our Nginx service image to be built.)
nginx.conf (Configuration file for our Nginx server.)
Inside nginx/Dockerfile
, paste the following:
FROM nginx:1.23
RUN rm /etc/nginx/conf.d/default.conf
COPY nginx.conf /etc/nginx/conf.d
Inside nginx/nginx.conf
, paste the following:
server {
listen 80 default_server;
location / {
proxy_pass http://web:8000;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $host;
}
location /static/ {
alias /home/app/code/static/;
}
}
The nginx.config
file specifies where our static files are stored and routes other requests to our web service.
Now build the images and run the containers. To do this, run:
docker-compose up --build
With this, you should have your development server running. Head over to http://127.0.0.1 to check it out.
...And that's it🎉. We have very quickly set up docker, docker-compose, and a reverse proxy server for our Django application.
Further Learning
For more detailed tutorials, you can checkout the following articles
Introduction to Elastic Beanstalk with Django, RDS, Docker, and Nginx at MoreAboutTech.
Dockerizing Django with Postgres, Gunicorn, and Nginx at TestDriven.
Dockerizing Django App at LogRocket.
If you found this article useful or learned something new, consider dropping a heart up and following me here on hashnode to keep up-to-date with any recent postings!
If there are certain topics you would also like me to cover and/or questions you may have, do drop a comment.
You can also find me on Twitter at akinsola232 and on LinkedIn at Ademola.
Till next time, happy coding!