How to write Dockerfile

Dockerfile is a blueprint of creating custom images, based on your requirements. A dockerfile contains which base image to start from, what dependencies to install, environment configuration, what commands to run on startup. Lets start with the basic keywords in writing dockerfiles.

Basics Keywords

FROM - To start with the base image

WORKDIR - To setup the working directory inside your container

COPY - Copy contents like application files/code to your image

RUN - Executing commands inside the image during build process

EXPOSE - Documenting the ports (This is not necessary. But a good practice)

ENV - Sets the environment variables

CMD - Define what happens when your container starts, but CMD sets default arguments which can be overwritten at runtime.

ENTRYPOINT - Define what happens when your container starts, but they are hard to overwrite at runtime and also not recommended.

ENTRYPOINT vs CMD

ENTRYPOINT

  • Used to specify the main binary/script to run inside the container.

CMD

  • Used to provide default arguments to ENTRYPOINT or default command if ENTRYPOINT doesn’t present.

Mini-Project

Let’s start writing Dockerfiles in real time with this simple project.

Clone this project — https://github.com/dockersamples/wordsmith

  1. Clone the above repo.

  2. Delete the Dockerfiles in api, web and db folders.

  3. Create you own Dockerfile in every path.

Postgres DB Dockerfile

## Start with the base image
FROM postgres:14.18

## Copy the words.sql to the image and execute at the start.
COPY words.sql /docker-entrypoint-initdb.d/init.sql

## Expose the port
EXPOSE 5432

API Dockefile

  • JAVA based docker image
# Multistage docker builds
## Base Image as builder
FROM maven:3.8.3-eclipse-temurin-17 AS builder
WORKDIR /apps
## COPY dependency injector
COPY pom.xml .
## COPY ./src to ./src directory
COPY ./src ./src
## RUN the maven command to create the .jar file
RUN mvn clean package -DskipTests

## Deployer
FROM eclipse-temurin:21-jre
WORKDIR /apps
## Copy the .jar file from builder to deployer
COPY --from=builder /apps/target/*.jar /apps/main.jar
EXPOSE 8080
## Specify the Entrypoint
ENTRYPOINT [ "java", "-jar", "/apps/main.jar" ]

Web Dockerfile

## Builder
## Base Image
FROM golang:1.22 AS builder
WORKDIR /app
COPY dispatcher.go .
RUN CGO_ENABLED=0 GOOS=linux go build -o dispatcher dispatcher.go

## Deployer
## Since go builds are executable directly, we can alpine images 
## to keep the image small.
FROM alpine:latest
WORKDIR /app
COPY ./static ./static
COPY --from=builder /app/dispatcher /app/dispatcher

EXPOSE 80
ENTRYPOINT ["/app/dispatcher"]

Basic docker commands for building images from docker files

# Basic command
docker build -t image-name .
# -t --> lets you specify the name and optional tag 

# specify custom dockerfile
docker build -f /home/user/Dockerfile-dev.txt -t myapp:dev .
# -f --> lets you specify the docker file in different path.

# building images without cache
docker build --no-cache -t my-app:1.0 .
0
Subscribe to my newsletter

Read articles from Rohit Kalyan Kandulapati directly inside your inbox. Subscribe to the newsletter, and don't miss out.

Written by

Rohit Kalyan Kandulapati
Rohit Kalyan Kandulapati