mirror of https://github.com/docker/cli.git
260 lines
18 KiB
Markdown
260 lines
18 KiB
Markdown
# build (legacy builder)
|
|
|
|
<!---MARKER_GEN_START-->
|
|
Build an image from a Dockerfile
|
|
|
|
### Aliases
|
|
|
|
`docker image build`, `docker build`, `docker builder build`
|
|
|
|
### Options
|
|
|
|
| Name | Type | Default | Description |
|
|
|:-----------------------------------------------------------------------------------------------------------------------------------------------------|:--------------|:----------|:------------------------------------------------------------------|
|
|
| [`--add-host`](https://docs.docker.com/reference/cli/docker/buildx/build/#add-host) | `list` | | Add a custom host-to-IP mapping (`host:ip`) |
|
|
| [`--build-arg`](https://docs.docker.com/reference/cli/docker/buildx/build/#build-arg) | `list` | | Set build-time variables |
|
|
| `--cache-from` | `stringSlice` | | Images to consider as cache sources |
|
|
| [`--cgroup-parent`](https://docs.docker.com/reference/cli/docker/buildx/build/#cgroup-parent) | `string` | | Set the parent cgroup for the `RUN` instructions during build |
|
|
| `--compress` | `bool` | | Compress the build context using gzip |
|
|
| `--cpu-period` | `int64` | `0` | Limit the CPU CFS (Completely Fair Scheduler) period |
|
|
| `--cpu-quota` | `int64` | `0` | Limit the CPU CFS (Completely Fair Scheduler) quota |
|
|
| `-c`, `--cpu-shares` | `int64` | `0` | CPU shares (relative weight) |
|
|
| `--cpuset-cpus` | `string` | | CPUs in which to allow execution (0-3, 0,1) |
|
|
| `--cpuset-mems` | `string` | | MEMs in which to allow execution (0-3, 0,1) |
|
|
| `--disable-content-trust` | `bool` | `true` | Skip image verification |
|
|
| [`-f`](https://docs.docker.com/reference/cli/docker/buildx/build/#file), [`--file`](https://docs.docker.com/reference/cli/docker/buildx/build/#file) | `string` | | Name of the Dockerfile (Default is `PATH/Dockerfile`) |
|
|
| `--force-rm` | `bool` | | Always remove intermediate containers |
|
|
| `--iidfile` | `string` | | Write the image ID to the file |
|
|
| [`--isolation`](#isolation) | `string` | | Container isolation technology |
|
|
| `--label` | `list` | | Set metadata for an image |
|
|
| `-m`, `--memory` | `bytes` | `0` | Memory limit |
|
|
| `--memory-swap` | `bytes` | `0` | Swap limit equal to memory plus swap: -1 to enable unlimited swap |
|
|
| [`--network`](https://docs.docker.com/reference/cli/docker/buildx/build/#network) | `string` | `default` | Set the networking mode for the RUN instructions during build |
|
|
| `--no-cache` | `bool` | | Do not use cache when building the image |
|
|
| `--platform` | `string` | | Set platform if server is multi-platform capable |
|
|
| `--pull` | `bool` | | Always attempt to pull a newer version of the image |
|
|
| `-q`, `--quiet` | `bool` | | Suppress the build output and print image ID on success |
|
|
| `--rm` | `bool` | `true` | Remove intermediate containers after a successful build |
|
|
| [`--security-opt`](#security-opt) | `stringSlice` | | Security options |
|
|
| `--shm-size` | `bytes` | `0` | Size of `/dev/shm` |
|
|
| [`--squash`](#squash) | `bool` | | Squash newly built layers into a single new layer |
|
|
| [`-t`](https://docs.docker.com/reference/cli/docker/buildx/build/#tag), [`--tag`](https://docs.docker.com/reference/cli/docker/buildx/build/#tag) | `list` | | Name and optionally a tag in the `name:tag` format |
|
|
| [`--target`](https://docs.docker.com/reference/cli/docker/buildx/build/#target) | `string` | | Set the target build stage to build. |
|
|
| `--ulimit` | `ulimit` | | Ulimit options |
|
|
|
|
|
|
<!---MARKER_GEN_END-->
|
|
|
|
## Description
|
|
|
|
> [!NOTE]
|
|
> This page refers to the **legacy implementation** of `docker build`,
|
|
> using the legacy (pre-BuildKit) build backend.
|
|
> This configuration is only relevant if you're building Windows containers.
|
|
>
|
|
> For information about the default `docker build`, using Buildx,
|
|
> see [`docker buildx build`](https://docs.docker.com/reference/cli/docker/build/).
|
|
|
|
When building with legacy builder, images are created from a Dockerfile by
|
|
running a sequence of [commits](./container_commit.md). This process is
|
|
inefficient and slow compared to using BuildKit, which is why this build
|
|
strategy is deprecated for all use cases except for building Windows
|
|
containers. It's still useful for building Windows containers because BuildKit
|
|
doesn't yet have full feature parity for Windows.
|
|
|
|
Builds invoked with `docker build` use Buildx (and BuildKit) by default, unless:
|
|
|
|
- You're running Docker Engine in Windows container mode
|
|
- You explicitly opt out of using BuildKit by setting the environment variable `DOCKER_BUILDKIT=0`.
|
|
|
|
The descriptions on this page only covers information that's exclusive to the
|
|
legacy builder, and cases where behavior in the legacy builder deviates from
|
|
behavior in BuildKit. For information about features and flags that are common
|
|
between the legacy builder and BuildKit, such as `--tag` and `--target`, refer
|
|
to the documentation for [`docker buildx build`](https://docs.docker.com/reference/cli/docker/buildx/build/).
|
|
|
|
### Build context with the legacy builder
|
|
|
|
The build context is the positional argument you pass when invoking the build
|
|
command. In the following example, the context is `.`, meaning current the
|
|
working directory.
|
|
|
|
```console
|
|
$ docker build .
|
|
```
|
|
|
|
When using the legacy builder, the build context is sent over to the daemon in
|
|
its entirety. With BuildKit, only the files you use in your builds are
|
|
transmitted. The legacy builder doesn't calculate which files it needs
|
|
beforehand. This means that for builds with a large context, context transfer
|
|
can take a long time, even if you're only using a subset of the files included
|
|
in the context.
|
|
|
|
When using the legacy builder, it's therefore extra important that you
|
|
carefully consider what files you include in the context you specify. Use a
|
|
[`.dockerignore`](https://docs.docker.com/build/concepts/context/#dockerignore-files)
|
|
file to exclude files and directories that you don't require in your build from
|
|
being sent as part of the build context.
|
|
|
|
#### Accessing paths outside the build context
|
|
|
|
The legacy builder will error out if you try to access files outside of the
|
|
build context using relative paths in your Dockerfile.
|
|
|
|
```dockerfile
|
|
FROM alpine
|
|
COPY ../../some-dir .
|
|
```
|
|
|
|
```console
|
|
$ docker build .
|
|
...
|
|
Step 2/2 : COPY ../../some-dir .
|
|
COPY failed: forbidden path outside the build context: ../../some-dir ()
|
|
```
|
|
|
|
BuildKit on the other hand strips leading relative paths that traverse outside
|
|
of the build context. Re-using the previous example, the path `COPY
|
|
../../some-dir .` evaluates to `COPY some-dir .` with BuildKit.
|
|
|
|
## Examples
|
|
|
|
### <a name="isolation"></a> Specify isolation technology for container (--isolation)
|
|
|
|
This option is useful in situations where you are running Docker containers on
|
|
Windows. The `--isolation=<value>` option sets a container's isolation
|
|
technology. On Linux, the only supported is the `default` option which uses
|
|
Linux namespaces. On Microsoft Windows, you can specify these values:
|
|
|
|
|
|
| Value | Description |
|
|
|-----------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
|
|
| `default` | Use the value specified by the Docker daemon's `--exec-opt` . If the `daemon` does not specify an isolation technology, Microsoft Windows uses `process` as its default value. |
|
|
| `process` | Namespace isolation only. |
|
|
| `hyperv` | Hyper-V hypervisor partition-based isolation. |
|
|
|
|
Specifying the `--isolation` flag without a value is the same as setting `--isolation="default"`.
|
|
|
|
### <a name="security-opt"></a> Optional security options (--security-opt)
|
|
|
|
This flag is only supported on a daemon running on Windows, and only supports
|
|
the `credentialspec` option. The `credentialspec` must be in the format
|
|
`file://spec.txt` or `registry://keyname`.
|
|
|
|
### <a name="squash"></a> Squash an image's layers (--squash) (experimental)
|
|
|
|
#### Overview
|
|
|
|
> [!NOTE]
|
|
> The `--squash` option is an experimental feature, and should not be considered
|
|
> stable.
|
|
|
|
Once the image is built, this flag squashes the new layers into a new image with
|
|
a single new layer. Squashing doesn't destroy any existing image, rather it
|
|
creates a new image with the content of the squashed layers. This effectively
|
|
makes it look like all `Dockerfile` commands were created with a single layer.
|
|
The `--squash` flag preserves the build cache.
|
|
|
|
Squashing layers can be beneficial if your Dockerfile produces multiple layers
|
|
modifying the same files. For example, files created in one step and
|
|
removed in another step. For other use-cases, squashing images may actually have
|
|
a negative impact on performance. When pulling an image consisting of multiple
|
|
layers, the daemon can pull layers in parallel and allows sharing layers between
|
|
images (saving space).
|
|
|
|
For most use cases, multi-stage builds are a better alternative, as they give more
|
|
fine-grained control over your build, and can take advantage of future
|
|
optimizations in the builder. Refer to the [Multi-stage builds](https://docs.docker.com/build/building/multi-stage/)
|
|
section for more information.
|
|
|
|
#### Known limitations
|
|
|
|
The `--squash` option has a number of known limitations:
|
|
|
|
- When squashing layers, the resulting image can't take advantage of layer
|
|
sharing with other images, and may use significantly more space. Sharing the
|
|
base image is still supported.
|
|
- When using this option you may see significantly more space used due to
|
|
storing two copies of the image, one for the build cache with all the cache
|
|
layers intact, and one for the squashed version.
|
|
- While squashing layers may produce smaller images, it may have a negative
|
|
impact on performance, as a single layer takes longer to extract, and
|
|
you can't parallelize downloading a single layer.
|
|
- When attempting to squash an image that doesn't make changes to the
|
|
filesystem (for example, the Dockerfile only contains `ENV` instructions),
|
|
the squash step will fail (see [issue #33823](https://github.com/moby/moby/issues/33823)).
|
|
|
|
#### Prerequisites
|
|
|
|
The example on this page is using experimental mode in Docker 23.03.
|
|
|
|
You can enable experimental mode by using the `--experimental` flag when starting
|
|
the Docker daemon or setting `experimental: true` in the `daemon.json` configuration
|
|
file.
|
|
|
|
By default, experimental mode is disabled. To see the current configuration of
|
|
the Docker daemon, use the `docker version` command and check the `Experimental`
|
|
line in the `Engine` section:
|
|
|
|
```console
|
|
Client: Docker Engine - Community
|
|
Version: 23.0.3
|
|
API version: 1.42
|
|
Go version: go1.19.7
|
|
Git commit: 3e7cbfd
|
|
Built: Tue Apr 4 22:05:41 2023
|
|
OS/Arch: darwin/amd64
|
|
Context: default
|
|
|
|
Server: Docker Engine - Community
|
|
Engine:
|
|
Version: 23.0.3
|
|
API version: 1.42 (minimum version 1.12)
|
|
Go version: go1.19.7
|
|
Git commit: 59118bf
|
|
Built: Tue Apr 4 22:05:41 2023
|
|
OS/Arch: linux/amd64
|
|
Experimental: true
|
|
[...]
|
|
```
|
|
|
|
#### Build an image with the `--squash` flag
|
|
|
|
The following is an example of a build with the `--squash` flag. Below is the
|
|
`Dockerfile`:
|
|
|
|
```dockerfile
|
|
FROM busybox
|
|
RUN echo hello > /hello
|
|
RUN echo world >> /hello
|
|
RUN touch remove_me /remove_me
|
|
ENV HELLO=world
|
|
RUN rm /remove_me
|
|
```
|
|
|
|
Next, build an image named `test` using the `--squash` flag.
|
|
|
|
```console
|
|
$ docker build --squash -t test .
|
|
```
|
|
|
|
After the build completes, the history looks like the below. The history could show that a layer's
|
|
name is `<missing>`, and there is a new layer with COMMENT `merge`.
|
|
|
|
```console
|
|
$ docker history test
|
|
|
|
IMAGE CREATED CREATED BY SIZE COMMENT
|
|
4e10cb5b4cac 3 seconds ago 12 B merge sha256:88a7b0112a41826885df0e7072698006ee8f621c6ab99fca7fe9151d7b599702 to sha256:47bcc53f74dc94b1920f0b34f6036096526296767650f223433fe65c35f149eb
|
|
<missing> 5 minutes ago /bin/sh -c rm /remove_me 0 B
|
|
<missing> 5 minutes ago /bin/sh -c #(nop) ENV HELLO=world 0 B
|
|
<missing> 5 minutes ago /bin/sh -c touch remove_me /remove_me 0 B
|
|
<missing> 5 minutes ago /bin/sh -c echo world >> /hello 0 B
|
|
<missing> 6 minutes ago /bin/sh -c echo hello > /hello 0 B
|
|
<missing> 7 weeks ago /bin/sh -c #(nop) CMD ["sh"] 0 B
|
|
<missing> 7 weeks ago /bin/sh -c #(nop) ADD file:47ca6e777c36a4cfff 1.113 MB
|
|
```
|
|
|
|
Test the image, check for `/remove_me` being gone, make sure `hello\nworld` is
|
|
in `/hello`, make sure the `HELLO` environment variable's value is `world`.
|