diff --git a/build/build.go b/build/build.go index 106c9a175d75..b951d1cc9213 100644 --- a/build/build.go +++ b/build/build.go @@ -782,6 +782,7 @@ func BuildWithResultHandler(ctx context.Context, nodes []builder.Node, opt map[s return res, nil } + buildRef := fmt.Sprintf("%s/%s/%s", node.Builder, node.Name, so.Ref) var rr *client.SolveResponse if resultHandleFunc != nil { var resultHandle *ResultHandle @@ -791,7 +792,6 @@ func BuildWithResultHandler(ctx context.Context, nodes []builder.Node, opt map[s rr, err = c.Build(ctx, *so, "buildx", buildFunc, ch) } if desktop.BuildBackendEnabled() && node.Driver.HistoryAPISupported(ctx) { - buildRef := fmt.Sprintf("%s/%s/%s", node.Builder, node.Name, so.Ref) if err != nil { return &desktop.ErrorWithBuildRef{ Ref: buildRef, @@ -811,6 +811,7 @@ func BuildWithResultHandler(ctx context.Context, nodes []builder.Node, opt map[s for k, v := range printRes { rr.ExporterResponse[k] = string(v) } + rr.ExporterResponse["buildx.build.ref"] = buildRef node := dp.Node().Driver if node.IsMobyDriver() { diff --git a/docs/reference/buildx_build.md b/docs/reference/buildx_build.md index bfa75e1e414c..b1605c1c1d05 100644 --- a/docs/reference/buildx_build.md +++ b/docs/reference/buildx_build.md @@ -327,6 +327,7 @@ $ cat metadata.json ```json { + "buildx.build.ref": "mybuilder/mybuilder0/0fjb6ubs52xx3vygf6fgdl611", "containerimage.config.digest": "sha256:2937f66a9722f7f4a2df583de2f8cb97fc9196059a410e7f00072fc918930e66", "containerimage.descriptor": { "annotations": { diff --git a/tests/bake.go b/tests/bake.go index 03c611b2f210..1cc20ef75f4f 100644 --- a/tests/bake.go +++ b/tests/bake.go @@ -1,6 +1,7 @@ package tests import ( + "encoding/json" "os" "path/filepath" "testing" @@ -34,6 +35,7 @@ var bakeTests = []func(t *testing.T, sb integration.Sandbox){ testBakeEmpty, testBakeShmSize, testBakeUlimits, + testBakeRefs, } func testBakeLocal(t *testing.T, sb integration.Sandbox) { @@ -586,3 +588,46 @@ target "default" { require.NoError(t, err) require.Contains(t, string(dt), `1024`) } + +func testBakeRefs(t *testing.T, sb integration.Sandbox) { + dockerfile := []byte(` +FROM scratch +COPY foo /foo + `) + bakefile := []byte(` +target "default" { +} +`) + dir := tmpdir( + t, + fstest.CreateFile("docker-bake.hcl", bakefile, 0600), + fstest.CreateFile("Dockerfile", dockerfile, 0600), + fstest.CreateFile("foo", []byte("foo"), 0600), + ) + + dirDest := t.TempDir() + + outFlag := "default.output=type=docker" + if sb.DockerAddress() == "" { + // there is no Docker atm to load the image + outFlag += ",dest=" + dirDest + "/image.tar" + } + + cmd := buildxCmd(sb, withDir(dir), withArgs("bake", "--metadata-file", filepath.Join(dirDest, "md.json"), "--set", outFlag)) + out, err := cmd.CombinedOutput() + require.NoError(t, err, out) + + dt, err := os.ReadFile(filepath.Join(dirDest, "md.json")) + require.NoError(t, err) + + type mdT struct { + Default struct { + BuildRef string `json:"buildx.build.ref"` + } `json:"default"` + } + var md mdT + err = json.Unmarshal(dt, &md) + require.NoError(t, err) + + require.NotEmpty(t, md.Default.BuildRef) +} diff --git a/tests/build.go b/tests/build.go index 88796b15f801..7e2f222124a5 100644 --- a/tests/build.go +++ b/tests/build.go @@ -48,6 +48,7 @@ var buildTests = []func(t *testing.T, sb integration.Sandbox){ testBuildOCIExportNotSupported, testBuildMultiPlatformNotSupported, testDockerHostGateway, + testBuildRef, } func testBuild(t *testing.T, sb integration.Sandbox) { @@ -279,23 +280,6 @@ RUN exit 1`) require.True(t, buildDetailsPattern.MatchString(string(out)), fmt.Sprintf("expected build details link in output, got %q", out)) } -func createTestProject(t *testing.T) string { - dockerfile := []byte(` -FROM busybox:latest AS base -COPY foo /etc/foo -RUN cp /etc/foo /etc/bar - -FROM scratch -COPY --from=base /etc/bar /bar -`) - dir := tmpdir( - t, - fstest.CreateFile("Dockerfile", dockerfile, 0600), - fstest.CreateFile("foo", []byte("foo"), 0600), - ) - return dir -} - func testBuildProgress(t *testing.T, sb integration.Sandbox) { dir := createTestProject(t) driver, _, _ := strings.Cut(sb.Name(), "+") @@ -432,3 +416,47 @@ RUN ping -c 1 buildx.host-gateway-ip.local require.NoError(t, err, string(out)) } } + +func testBuildRef(t *testing.T, sb integration.Sandbox) { + dir := createTestProject(t) + dirDest := t.TempDir() + + outFlag := "--output=type=docker" + if sb.DockerAddress() == "" { + // there is no Docker atm to load the image + outFlag += ",dest=" + dirDest + "/image.tar" + } + + cmd := buildxCmd(sb, withArgs("build", outFlag, "--metadata-file", filepath.Join(dirDest, "md.json"), dir)) + out, err := cmd.CombinedOutput() + require.NoError(t, err, string(out)) + + dt, err := os.ReadFile(filepath.Join(dirDest, "md.json")) + require.NoError(t, err) + + type mdT struct { + BuildRef string `json:"buildx.build.ref"` + } + var md mdT + err = json.Unmarshal(dt, &md) + require.NoError(t, err) + + require.NotEmpty(t, md.BuildRef) +} + +func createTestProject(t *testing.T) string { + dockerfile := []byte(` +FROM busybox:latest AS base +COPY foo /etc/foo +RUN cp /etc/foo /etc/bar + +FROM scratch +COPY --from=base /etc/bar /bar +`) + dir := tmpdir( + t, + fstest.CreateFile("Dockerfile", dockerfile, 0600), + fstest.CreateFile("foo", []byte("foo"), 0600), + ) + return dir +}