Dockerfile Best Practices

Write efficient Dockerfiles with best practices: layer ordering, caching, .dockerignore, non-root users, health checks, and security hardening.

Build

Detailed Explanation

Dockerfile Best Practices

1. Use Specific Base Image Tags

# BAD: unpredictable
FROM node:latest

# GOOD: pinned version
FROM node:20.11-alpine3.19

2. Order Layers by Change Frequency

Put rarely-changing instructions first to maximize cache hits:

FROM node:20-alpine
WORKDIR /app

# These change rarely - cached
COPY package.json package-lock.json ./
RUN npm ci --production

# This changes often - rebuilds from here
COPY . .

3. Minimize Layer Count

Combine related commands in a single RUN:

# BAD: 3 layers
RUN apt-get update
RUN apt-get install -y curl
RUN rm -rf /var/lib/apt/lists/*

# GOOD: 1 layer
RUN apt-get update && \
    apt-get install -y --no-install-recommends curl && \
    rm -rf /var/lib/apt/lists/*

4. Use .dockerignore

node_modules
.git
.env
*.md
dist
.DS_Store

5. Run as Non-Root

RUN addgroup -S appgroup && adduser -S appuser -G appgroup
USER appuser

6. Add Health Checks

HEALTHCHECK --interval=30s --timeout=3s --retries=3 \
  CMD wget --no-verbose --tries=1 --spider http://localhost:3000/health || exit 1

7. Use COPY Instead of ADD

# Prefer COPY for simple file copying
COPY ./config /app/config

# Use ADD only for tar extraction
ADD archive.tar.gz /opt/

8. Set Appropriate Labels

LABEL org.opencontainers.image.source="https://github.com/org/repo"
LABEL org.opencontainers.image.version="1.0.0"
LABEL org.opencontainers.image.description="My application"

Use Case

Writing production-grade Dockerfiles that build faster, produce smaller images, follow security best practices, and are maintainable by teams.

Try It — Docker CLI Reference

Open full tool