C.W.K.
Stream
Lesson 05 of 06 · published

Base Image Choice — full / slim / alpine / distroless / scratch

~14 min · dockerfile, size, security

Level 0Container Curious
0 XP0/36 lessons0/10 achievements
0/120 XP to next level120 XP to go0% complete

Base images, smallest to largest

ImageSizeBest for
scratch0 bytesStatic binaries (Go, Rust)
distroless~20MBHardened production, minimal attack surface
alpine~5-50MBGo, Rust, simple Node. Tricky for Python (musl).
*-slim~50-150MBMost apps. The right default.
full (e.g. python:3.12)~500MB-1GBDev environments, when you need build tools

The trade-offs are real

alpine uses musl libc, not glibc. Many Python wheels are glibc-only — pip will fall back to compiling from source on alpine. That can blow your build time up by 10x. For Go and Rust (which produce static binaries), alpine is great. For Python apps, prefer -slim unless you really know what you're getting into.

distroless images have no shell, no package manager. You can't docker exec -it ... bash into them. Great for production hardening. Painful for ad-hoc debugging.

scratch is literally empty. Only static binaries with no dynamic linking work. Maximum minimalism, only for the right tool.

Code

Same Python app, four bases·dockerfile
# 1. python:3.12 (full)         -> ~1GB final image
# 2. python:3.12-slim           -> ~150MB
# 3. python:3.12-alpine         -> ~50MB but pip might compile wheels
# 4. gcr.io/distroless/python3  -> ~50MB, no shell

# Recommendation for most Python apps:
FROM python:3.12-slim
# Solid balance of size, compatibility, debuggability.
Go: where scratch shines·dockerfile
FROM golang:1.23-alpine AS builder
WORKDIR /src
COPY go.mod go.sum ./
RUN go mod download
COPY . .
RUN CGO_ENABLED=0 go build -o /app ./cmd/server

FROM scratch
COPY --from=builder /app /app
ENTRYPOINT ["/app"]

# Final image is just the Go binary. Maybe 15MB.
# No shell, no libc, no anything. Maximum minimalism.

External links

Exercise

Pick one of your Python or Go projects. Build it on (a) full base, (b) slim, (c) alpine. Record build times and final image sizes. For Python, note any wheels that ended up compiling from source on alpine. Pick the right base for production and write 2 sentences justifying it.

Progress

Progress is local-only — sign in to sync across devices.
Spotted a bug or have feedback on this page?Report an Issue

Comments 0

🔔 Reply notifications (sign in)
Sign inPlease sign in to comment.

No comments yet — be the first.