How to Create a Dockerfile?

Docker allows developers to build, test, and deploy applications quickly and efficiently using isolated and portable containers that run anywhere.

Docker is an open-source tool that packages application(s), all the required packages, and its base operating system into containerized packages. As Docker containers are standalone, they run on any system without any need for reconfiguration.

Docker builds containers from images. A Docker image is a standalone package that defines all the requirements needed to run an application, such as operating system, runtime, system tools, libraries, configurations, and more. Docker converts the images to containers during runtime.

Docker builds images from configurations defined in a Dockerfile. A Dockerfile is simply a configuration file that states all the instructions on creating a Docker image. As a result, building Docker images using a Dockerfile is easier and much more efficient.

This guide will walk you through creating a Dockerfile and using it to build a docker image.

Dockerfile Format

The Dockerfile is a raw text document. Entries in the Dockerfile are in the following format:

$ INSTRUCTION argument(s)

The first part defines the docker commands you can use in a docker shell. The second represents the arguments or specific values to pass to the primary instruction.

NOTE: The instructions are not case-sensitive. However, Docker recommends using UPPERCASE to distinguish them from arguments.

The following are some popular instructions in a Dockerfile.

FROM – This instruction defines the parent image for subsequent instructions. FROM clause must be the first entry in a Dockerfile. It can come after a comment or parse directive or ARG used in the FROM directive.

ARG – It defines variables used during the build once you run Docker build command on the file.

CMD – This sets the command executed upon container creation. Docker only allows one CMD instruction per file. When you have more than one defined, it runs the last command.

LABEL – The label instruction defines metadata information for the image. You can add as many labels as you see fit in the form of key-value pairs. For example, image metadata could include the version number, author information, description, etc.

RUN – Sets the instructions to be executed during the image build.

USER – This instruction sets the username or UID of the user when running the image or instructions in a Dockerfile such as CMD, RUN, and ENTRYPOINT.

ENTRYPOINT – It defines the commands Docker executes upon container creation. Options are overridable in the command line during container startup.

ADD – This instruction copies files and directories from the specified source to a specified destination. The source can be a local path or an external URL. If the files are archives, Docker automatically unpacks them into the image.

VOLUME – The volume instructions allow you to create mount points from host machine directories or other containers.

EXPOSE – This instruction tells Docker which port to listen on during runtime.

ENV – It sets environment variables.

WORKDIR – sets the current working directory. If the directory specified does not exist, Docker will automatically create one.

The above are some standard instructions you can use in a Dockerfile.

How to Create a Dockerfile

The process of creating a Dockerfile is straightforward. Start by creating a working directory for your Docker operations. Next, create a Dockerfile and edit it with your favorite text editor.

$ cd ~
$ mkdir Docker
$ cd Docker
$ touch Dockerfile
$ vim Dockerfile

We start by getting the base image from the Docker Hub. We can do this by using the FROM instruction in the Dockerfile.

In this example, we will create a simple container containing running Nginx server on Debian 10 image.

Debian 10 image on Docker Hub

Edit the Dockerfile and add the following entries.

FROM  ebian:10.9
RUN apt-get update && \
    apt-get install -y nginx \
    LABEL maintainer=”linuxhint”
LABEL version=”1.0
LABEL description=”A simple image running Nginx on Debain 10
EXPOSE 80/tcp
CMD [“nginx”, “-g”, ‘daemon off;’]

In the above Dockerfile, we start by defining the base image (Debian 10.9)

We run various apt commands to update packages and install Nginx Web-Server.

We then add metadata information about the image, including the maintainer, version, and description.

Finally, we set the expose port, and the command turns off the Nginx daemon. The command above prevents the container from halting.

Save the file and run the docker build against the file.

How to Build A Dockerfile Image

Once we have the Dockerfile complete, we can proceed to build the image. Run the command Docker build inside the Docker directory:

$ cd ~/Docker
$ docker build –pull –rm -f “Dockerfile” -t docker:latest “.”

In the above command, we use the docker build command and pass various options. For example, the –pull tells Docker to try and pull the latest version of the image.

The –rm removes immediate containers after the image build process is complete.

-f specifies the Dockerfile name.

Finally, the -t option sets the tag for the image.

The above commands will successfully build the image and store it in your local disk.

You can verify the image exists by calling the command:

$ docker image ls
$ docker       latest    162e94589bec   2 minutes ago   233MB

How to Create a Docker Container

Now that we have the image from the Dockerfile, we can go ahead and spawn a container. To do this, we use the docker run command as:

$ docker run  -p 80:80 --name nginx docker

The commands above will launch the container with the name nginx and bind the container to port 80.

To show running containers, use the command:

$ docker container ls
1c90266035b5   nginx:latest    57 seconds ago   Up 56 seconds   80/tcp    nginx

The command above shows the nginx container up and running.


This tutorial covered writing Dockerfiles, creating images, and running a Docker container from the images. To learn more about Dockerfiles, consider the documentation.

About the author

John Otieno

My name is John and am a fellow geek like you. I am passionate about all things computers from Hardware, Operating systems to Programming. My dream is to share my knowledge with the world and help out fellow geeks. Follow my content by subscribing to LinuxHint mailing list