<commit_before>---
title: Multi-stage builds
description: Keeping your images small with multi-stage builds
keywords: build, best practices
redirect_from:
- /engine/userguide/eng-image/multistage-build/
- /develop/develop-images/multistage-build/
---

Multi-stage builds are useful to anyone who has struggled to optimize
Dockerfiles while keeping them easy to read and maintain.

> **Acknowledgment**
>
> Special thanks to [<NAME>](https://twitter.com/alexellisuk) for granting
> permission to use his blog post [Builder pattern vs. Multi-stage builds in Docker](https://blog.alexellis.io/mutli-stage-docker-builds/)
> as the basis of the examples below.

## Before multi-stage builds

One of the most challenging things about building images is keeping the image
size down. Each instruction in the Dockerfile adds a layer to the image, and you
need to remember to clean up any artifacts you don't need before moving on to
the next layer. To write a really efficient Dockerfile, you have traditionally
needed to employ shell tricks and other logic to keep the layers as small as
possible and to ensure that each layer has the artifacts it needs from the<commit_msg>Clarify dockerfile instructions<commit_after>---
title: Multi-stage builds
description: Keeping your images small with multi-stage builds
keywords: build, best practices
redirect_from:
- /engine/userguide/eng-image/multistage-build/
- /develop/develop-images/multistage-build/
---

Multi-stage builds are useful to anyone who has struggled to optimize
Dockerfiles while keeping them easy to read and maintain.

> **Acknowledgment**
>
> Special thanks to [<NAME>](https://twitter.com/alexellisuk) for granting
> permission to use his blog post [Builder pattern vs. Multi-stage builds in Docker](https://blog.alexellis.io/mutli-stage-docker-builds/)
> as the basis of the examples below.

## Before multi-stage builds

One of the most challenging things about building images is keeping the image
size down. Each `RUN`, `COPY`, and `ADD` instruction in the Dockerfile adds a layer to the image, and you
need to remember to clean up any artifacts you don't need before moving on to
the next layer. To write a really efficient Dockerfile, you have traditionally
needed to employ shell tricks and other logic to keep the layers as small as
possible and to ensure that each layer has the artifacts it needs from the
{'fraction_non_alphanumeric': 0.06905263157894737, 'fraction_numerical': 0.0, 'mean_word_length': 4.590588235294118, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 15, 'https://': 4, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '7531113', 'n_tokens_mistral': 638, 'n_tokens_neox': 599, 'n_words': 311}