#Using Dagger only to create the image, not a container

1 messages ยท Page 1 of 1 (latest)

true urchin
#

Hi there,

I'm working on a build CI pipeline that takes customer Dockerfiles and publishes them. The issue lies in the fact DockerBuild() not only converts the Dockerfile to an "image", but rather produces a container of it. That invokes, of course, the entrypoint and command lines.

It's very plausible customers will have entrypoints and commands set up to only succeed when they are run from the deployed k8s environment, for example. We can ignore these failures, but then I don't know if we have any good way of knowing whether or not the image was constructed successfully prior to publishing.

Is there no way to simply construct the image via Dagger vs creating a container of it? Is there any thought put into this use case?

night comet
#

Hi Rosy ๐Ÿ™‚ In Dagger, container and image are the same thing. If you don't want to execute the entrypoint, use Sync. This is explained in https://github.com/dagger/dagger/issues/4668#build:

- _, err = client.Container().Build(src).ExitCode(ctx)
+ _, err = client.Container().Build(src).Sync(ctx)
GitHub

Summary Developers are often confused by a property of the Dagger engine called "laziness": pipelines are executed at the latest possible moment, to maximize performance. There are severa...

true urchin
#

Hi Helder - nice! That is definitely on the right track for what we're looking for. Apologies for not finding this myself ๐Ÿ˜… This skips the entrypoint, but the underlying CMD still executes, unfortunately.

night comet
#

Really? Can I see your pipeline?

#

To be clear, did you notice me pointing out that it's the last diff in that section? ๐Ÿ‘‡

- _, err = client.Container().Build(src).ExitCode(ctx)
+ _, err = client.Container().Build(src).Sync(ctx)
true urchin
#

Sure, here's the basic outline of the Dockerfile

FROM base-image
COPY app/ app/

The CMD is actually set in the base-image, so it's being inherited. Let's pretend it's something that would fail given the current environment.

We're running this:

container, err := client.Host().Directory(".").DockerBuild().Sync(context.Background())
if err != nil {
  fmt.Println(err)
  return
}

In this scenario, the underlying command is still running (and failing). That is not captured in err (but is in StdOutput()).

#

So to be clear, the image is being built correctly. It just then runs the command which produces an error. So I can publish/export this image and it's all good. The issue is differentiating between when the construction of the container has an error because of the dockerfile or because of trying to run the command. Basically the only difference we've found so far is when we export it, the tarfile is empty

night comet
#

You can clear the CMD before building, but that shouldn't be an issue with Sync. I'll need to repro it.

true urchin
#

The problem with clearing the CMD is that I want to preserve it in the final image I publish/export (since we're building this as an application image on behalf of someone else).

So we'd have to do something like override the command, build it, then re-input the command before publication if that's possible

night comet
#

I see. So you don't need Sync, you actually just want Publish? Should be the same anyway.

#

Can you check if you're failing on a RUN instead of CMD?

true urchin
#

Ah- I actually wonder if this is an embarrassing user fault. I think Sync is working as intended

#

we build, then run call container.StdOut(). As I read more carefully, I see this invokes the default command if none are executed

#

I think we can rely on the error returned from Sync() to determine if the container built successfully, and ignore StdOut

night comet
#

Oh, yes that explains it! ๐Ÿ™‚

true urchin
#

I appreciate the help!