What is a multi-stage build in Docker and why use it?
A multi-stage build uses several FROM lines in one Dockerfile. You compile in a heavy build stage, then COPY --from only the finished output into a small final stage, so compilers and source never ship.
Explain it simply
Think of a wedding caterer. The big kitchen has stoves, knives and sacks of flour, but only the finished dishes travel to the venue. A multi-stage build keeps the kitchen behind and ships the dishes.
Each FROM starts a new stage with its own filesystem. Early stages can use a large image with the JDK, Node and build tools. The last stage starts from a small base and copies in just the artefact with COPY --from=build. Anything not copied, such as source code, dev dependencies and caches, is dropped. The result is smaller, faster to pull, and has less attack surface.
You can name stages with AS and stop at one with docker build --target build ., handy for running tests in CI.
Example
FROM maven:3.9-eclipse-temurin-21 AS build
WORKDIR /src
COPY . .
RUN mvn -q package -DskipTests
FROM eclipse-temurin:21-jre-alpine
COPY --from=build /src/target/app.jar /app.jar
CMD ["java", "-jar", "/app.jar"]What to say in the interview
"A multi-stage build has several FROM stages. I build with the full toolchain in one stage and copy only the output into a minimal final stage using COPY --from. That cuts image size and attack surface, because compilers and source code never reach production."
Common mistakes
- Forgetting that only the last stage becomes the final image unless you pass --target.