-
Notifications
You must be signed in to change notification settings - Fork 493
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Multiple targets bake is slow to send context even if all targets use the same. #1377
Comments
Same as #92 You can see the previous work linked there. This is possible in buildkit side, but maybe could use reevaluation of the design. You can make builds with shared sessions but I think the cases that are not possible atm would be when two builds share the same build context but want to pass different secrets(as both as sent via session). I know @aaronlehmann uses the shared session implementation so maybe he has some ideas here. With the current buildkit implementation, if we detect the chases where parallel builds are sharing the session fully(we need to check that they all use the same build secrets/ssh config, as well as the same build context of course) we could make them use the shared session. |
Thank you @tonistiigi for the detailed feedback! Of course that would be awesome if bake could sort out by itself that sessions can be shared safely. First, I thought I could "just" add this |
This should be possible on the buildkit side if buildx would pass the correct argument (and define how user describes this case). The problem with this is though that context can be selectively transferred based on what files the dockerfile stages use. Maybe it makes more sense to just use a base stage in a Dockerfile that figures what files are needed. Smth. like: from alpine as base
copy . /ctx
from base as target1
run apk add git
run ls -l /ctx
from base as target2
run apk add curl
run ls -l /ctx group "default" {
targets = ["target1", "target2"]
}
target "base" {
target = "base"
}
target "target1" {
target = "target1"
contexts = {
base = "target:base"
}
}
target "target2" {
target = "target2"
contexts = {
base = "target:base"
}
} If just using context makes more sense from alpine as base
from scratch as ctx
copy . .
from base as target1
run apk add git
run --mount=target=ctx,from=ctx ls -l
from base as target2
run apk add curl
run --mount=target=ctx ls -l /ctx group "default" {
targets = ["target1", "target2"]
}
target "ctx" {
target = "ctx"
}
target "target1" {
target = "target1"
contexts = {
ctx = "target:ctx"
}
}
target "target2" {
target = "target2"
contexts = {
ctx = "target:ctx"
}
} |
I tried the last example with
and looks like it is smart enough to completely optimize out the copy step in that case and both targets just use the context directly. |
+1 for fixing this issue; this is a massive issue for us. Context transfer for 15 parallel builds of our images takes around ~200 seconds which is insane. Our dockerfile build is slower than our entire bazel build of the project, and all our dockerfiles are just copying the build artefacts. We reduced parallelism to reduce build time, but the context transfer still takes much time. I would love to see this issue resolved! We're thinking of completely switching to podman with volume mounts and |
I've got a bake build that builds around 20 targets concurrently.
All of the targets share the same context, a Go project of around 100Mb.
When I run buildx bake, it's visible that it sends the same context to the buildkit, for each target.
I thought it was the logs that made me believe it was so but that underneath it was all fine and sent only once.
So I created a "minimal" test project with 40 targets building the same
Go sources. I added a 100Mb useless file to the context.
docker buildx bake -f slow.hcl --load
takes multiple minutes to complete and we can see that the context is being sent 40 times.I tested another option where I add a
base
target to the bakefile, copy the whole context into that image and made the Dockerfile copy from this target instead of directly from .Now, the build is way less verbose and finished in 19s with:
BASE="target:base" docker buildx bake -f slow.hcl --load
By the way, this workaround requires changing all my Dockerfiles. Every
COPY x y
becomesCOPY --from=base x y
. It would be much simpler if we could redefine the "." context and set it to "target:base" using build-contexts flags.Another thing interesting is how the build takes 19s and if you sum up the build logs, you've got 4.7s.
Versions used:
The text was updated successfully, but these errors were encountered: