Buildkit does not allow ONBUILD RUN --mount...
Problem
The buildkit does not allow mounting an image to an ONBUILD RUN command. When I mount an image in an ONBUILD RUN command, then use that as a base for another image, I get the following error:
=> ERROR [2/1] RUN --mount=type=bind,from=tomcat:latest,src=/usr/local/tomcat/BUILDING.txt,dst=/BUILDING.txt 0.2s ------ > [2/1] RUN --mount=type=bind,from=tomcat:latest,src=/usr/local/tomcat/BUILDING.txt,dst=/BUILDING.txt: #7 0.125 container_linux.go:344: starting container process caused "process_linux.go:424: container init caused \"rootfs_linux.go:58: mounting \\\"/var/lib/docker/tmp/buildkit-mount356322217/usr/local/tomcat/BU ILDING.txt\\\" to rootfs \\\"/var/lib/docker/buildkit/executor/y76nt87kgf7bikqmd23wzq8ed/rootfs\\\" at \\\"/BUILDING.txt\\\" caused \\\"stat /var/lib/docker/tmp/buildkit-mount356322217/usr/local/tomcat/BUILDING .txt: no such file or directory\\\"\"" --------
Steps To Reproduce
I have a "base" dockerfile that looks like this:
# syntax = docker/dockerfile:1.0-experimental FROM ubuntu:16.04
ONBUILD RUN --mount=type=bind,from=tomcat:latest,src=/usr/local/tomcat/BUILDING.txt,dst=/BUILDING.txt
Then I have a service dockerfile that looks like this:
# syntax = docker/dockerfile:1.0-experimental
FROM base
Attempting to build this service image produces the above error.
Use Case
I am trying to create a base image for several services used by my company. That base image is supposed to contain all the building blocks needed to run the service, but should not actually build them (hence the use of the ONBUILD command). So we start with an operating system and layer in standard shared utilities and/or files. Each service uses this base image, then adds in only service-specific files.
@tonistiigi Do we plan to support this?
@AkihiroSuda I think yes. Haven't checked what is the issue here. Ideally, we could also have something like ONBUILD++ where ONBUILD from any frontend could be used inside any other frontend but that's a bit more tricky and requires changing what is stored in the image config. Simple examples in https://github.com/moby/buildkit/issues/817 .
Stumbled upon this today, my idea of onbuild run mount is like this
ONBUILD WORKDIR /deps
ONBUILD ENV COMPOSER_HOME=/tmp/composer
ONBUILD COPY composer.json .
ONBUILD COPY composer.lock .
ONBUILD RUN --mount=type=cache,target=/tmp/composer/cache \
--mount=type=cache,target=/deps/vendor \
composer install --no-scripts --no-dev --prefer-dist --optimize-autoloader;
to make a simplified dockerfile that can be used with just
FROM laravel:8.1
in each project, but it seems it doesnt support it ?
[fikrimi@crimson:blog]$ docker build -t test -f .docker/Dockerfile .
[+] Building 0.0s (2/2) FINISHED docker:default
=> [internal] load build definition from Dockerfile 0.0s
=> => transferring dockerfile: 97B 0.0s
=> [internal] load metadata for docker.io/library/laravel:8.1 0.0s
Dockerfile:1
--------------------
1 | >>> FROM laravel:8.1
2 | ENV OPENSSL_CONF=/var/www/html/openssl.conf
--------------------
ERROR: failed to solve: cannot mount from stage "scratch" to "/tmp/composer", stage needs to be defined before current command
Version: Docker version 26.0.0, build 2ae903e86c
Wanted to add that we are noticing the same as @fmiqbal with Docker version >=26.0.0. For example with this Dockerfile:
FROM ubuntu:22.04 as base
ONBUILD RUN \
--mount=type=cache,target=/var/cache/apt \
apt-get update && apt-get install -y git
FROM base as test
WORKDIR /app
RUN echo "this is the stuff" > notes.txt
ENTRYPOINT [ "cat", "notes.txt" ]
docker build -t mytest --target test . will succeed with Docker 25.0.1 but fail with Docker 26.0.1. Error message:
$ docker build -t mytest --target test .
[+] Building 0.0s (2/2) FINISHED docker:default
=> [internal] load build definition from Dockerfile 0.0s
=> => transferring dockerfile: 280B 0.0s
=> [internal] load metadata for docker.io/library/ubuntu:22.04 0.0s
Dockerfile:7
--------------------
5 | apt-get update && apt-get install -y git
6 |
7 | >>> FROM base as test
8 |
9 | WORKDIR /app
--------------------
ERROR: failed to solve: cannot mount from stage "scratch" to "/var/cache/apt", stage needs to be defined before current command
Seeing the same issue as @fmiqbal and @hansenms when using: # syntax=docker/dockerfile:1.7.0
Dockerfile 1.6.0 works fine.
FYI this is still an issue with dockerfile:1.8.1
Maybe related to #4568