Writing Dockerfiles for Python application
Ujjwal Goyal
Posted on June 16, 2021
Note: The original code is from Udacity's Cloud Native Fundamentals Nanodegree Scholarship Program. The referenced files can be found here.
This post does not provide instructions on installing Docker. For assistance, please refer here.
In this post we're going to go through the process of running a simple Python web app on a container. But, what is a container?
Containers
A container is a standard unit of software that packages up code and all its dependencies so the application runs quickly and reliably from one computing environment to another. (Source: Docker)
As containers run on the same operating system, they require fewer resources than virtual machines. (Source: Wikipedia)
Python application
Let's start with a simple Python web application that serves a single endpoint. We save this file as app.py
.
from flask import Flask
app = Flask(__name__)
@app.route("/")
def hello():
return "Hello World"
if __name__ == "__main__":
app.run(host='0.0.0.0')
On running the command python3 app.py
, we can open our browser and on checking http://0.0.0.0:5000/
(or http://localhost:5000/
), we get a simple web page with the text "Hello World"!!
(We use port 5000, as it is the default port for Flask. For more about getting started with Flask, please see here.)
Since we're importing the Flask package, we need a file that contains the requirements for the app to run.
Create a new file named requirements.txt
with the contents
Flask==1.1.1
where 1.1.1 is the Flask version. Feel free to use a different version! We'll use this file later for our Dockerfile.
Now that we have a working application, we can get started on containerizing it!
Building an image
A container image is a lightweight, standalone, executable package of software that includes everything needed to run an application: code, runtime, system tools, system libraries and settings. (Source: Docker)
To build an image, we require a Dockerfile, which is a text-based script of instructions (Source: Docker Docs).
To start with, our Dockerfile requires a parent image on top of which our instructions will run (more info here).
FROM python:3.8-alpine3.12
Here, python
is the image name, while 3.8-alpine3.12
is the tag. An image can have various tags, representing different versions of the image. Alpine images are smaller in size than normal images.
An optional step is to add a label to the image.
FROM python:3.8-alpine3.12
LABEL developer="importhuman"
Next, we need to copy the contents from our local directory to the container directory.
FROM python:3.8-alpine3.12
LABEL developer="importhuman"
COPY . /app
This copies all contents from the current directory, to a new directory named /app
on the container.
Next, we set this directory as our working directory. All further instructions will be carried out in this directory.
FROM python:3.8-alpine3.12
LABEL developer="importhuman"
COPY . /app
WORKDIR /app
The container needs to install dependencies to run the application successfully. So, we add a command to carry out the installation.
FROM python:3.8-alpine3.12
LABEL developer="importhuman"
COPY . /app
WORKDIR /app
RUN pip install -r requirements.txt
All these steps will build the image. To run the image and hence the container, we add the final step.
FROM python:3.8-alpine3.12
LABEL developer="importhuman"
COPY . /app
WORKDIR /app
RUN pip install -r requirements.txt
CMD ["python3", "app.py"]
Our instructions are ready. Now, we can build our image!
In the command line, run the following command:
docker build -t image-name path/to/image
-t image-name
gives your image the name "image-name", thus you can give it whatever name you'd like!
path/to/image
is the path to the directory containing the Dockerfile. If you're running the command in the same directory as the Dockerfile, replace path/to/image
with a dot.
Now, you can run docker images
and you should be able to see your newly built image!
Posted on June 16, 2021
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.