Script 'mail_helper' called by obssrc Hello community, here is the log from the commit of package apko for openSUSE:Factory checked in at 2024-12-12 21:19:24 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/apko (Old) and /work/SRC/openSUSE:Factory/.apko.new.29675 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "apko" Thu Dec 12 21:19:24 2024 rev:27 rq:1230280 version:0.21.0 Changes: -------- --- /work/SRC/openSUSE:Factory/apko/apko.changes 2024-12-11 21:09:07.268951435 +0100 +++ /work/SRC/openSUSE:Factory/.apko.new.29675/apko.changes 2024-12-12 21:19:26.231831626 +0100 @@ -1,0 +2,6 @@ +Thu Dec 12 05:54:50 UTC 2024 - opensuse_buildserv...@ojkastl.de + +- Update to version 0.21.0: + * Make LockImageConfiguration multi-arch aware (#1432) + +------------------------------------------------------------------- Old: ---- apko-0.20.2.obscpio New: ---- apko-0.21.0.obscpio ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ apko.spec ++++++ --- /var/tmp/diff_new_pack.moqDIz/_old 2024-12-12 21:19:27.187871463 +0100 +++ /var/tmp/diff_new_pack.moqDIz/_new 2024-12-12 21:19:27.187871463 +0100 @@ -17,7 +17,7 @@ Name: apko -Version: 0.20.2 +Version: 0.21.0 Release: 0 Summary: Build OCI images from APK packages directly without Dockerfile License: Apache-2.0 ++++++ _service ++++++ --- /var/tmp/diff_new_pack.moqDIz/_old 2024-12-12 21:19:27.227873129 +0100 +++ /var/tmp/diff_new_pack.moqDIz/_new 2024-12-12 21:19:27.231873296 +0100 @@ -3,7 +3,7 @@ <param name="url">https://github.com/chainguard-dev/apko</param> <param name="scm">git</param> <param name="exclude">.git</param> - <param name="revision">v0.20.2</param> + <param name="revision">v0.21.0</param> <param name="versionformat">@PARENT_TAG@</param> <param name="versionrewrite-pattern">v(.*)</param> <param name="changesgenerate">enable</param> ++++++ _servicedata ++++++ --- /var/tmp/diff_new_pack.moqDIz/_old 2024-12-12 21:19:27.259874462 +0100 +++ /var/tmp/diff_new_pack.moqDIz/_new 2024-12-12 21:19:27.263874629 +0100 @@ -1,6 +1,6 @@ <servicedata> <service name="tar_scm"> <param name="url">https://github.com/chainguard-dev/apko</param> - <param name="changesrevision">c26998241454be4057bc100ce1062aaabd9bb944</param></service></servicedata> + <param name="changesrevision">d45b6da444f211f49e25d25d26cc0241023d22c8</param></service></servicedata> (No newline at EOF) ++++++ apko-0.20.2.obscpio -> apko-0.21.0.obscpio ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/apko-0.20.2/pkg/build/lock.go new/apko-0.21.0/pkg/build/lock.go --- old/apko-0.20.2/pkg/build/lock.go 2024-12-11 01:41:22.000000000 +0100 +++ new/apko-0.21.0/pkg/build/lock.go 2024-12-11 23:02:06.000000000 +0100 @@ -17,6 +17,7 @@ import ( "context" "fmt" + "maps" "reflect" "regexp" "sort" @@ -27,13 +28,19 @@ "chainguard.dev/apko/pkg/build/types" ) -func LockImageConfiguration(ctx context.Context, ic types.ImageConfiguration, opts ...Option) (*types.ImageConfiguration, map[string][]string, error) { +// LockImageConfiguration returns a map of locked image configurations for each architecture, +// plus an entry for the "index" pseudo-architecture that represents the intersection of packages +// across all the real architecture configs. It also returns a map of missing packages for each +// architecture that could not be locked. Using the "index" architecture is equivalent to what +// this used to return prior to supporting per-arch locked configs. +func LockImageConfiguration(ctx context.Context, ic types.ImageConfiguration, opts ...Option) (map[string]*types.ImageConfiguration, map[string][]string, error) { mc, err := NewMultiArch(ctx, ic.Archs, append(opts, WithImageConfiguration(ic))...) if err != nil { return nil, nil, err } archs := make([]resolved, 0, len(ic.Archs)) + ics := make(map[string]*types.ImageConfiguration, len(ic.Archs)+1) // Determine the exact versions of our transitive packages and lock them // down in the "resolved" configuration, so that this build may be @@ -72,14 +79,30 @@ archs = append(archs, r) } - l, missing, err := unify(ic.Contents.Packages, archs) + pls, missing, err := unify(ic.Contents.Packages, archs) if err != nil { return nil, missing, err } - // Set the locked package list. - ic.Contents.Packages = l - return &ic, missing, nil + // Set the locked package lists. + for arch, pl := range pls { + // Create a defensive copy of "ic". + copied := types.ImageConfiguration{} + if err := ic.MergeInto(&copied); err != nil { + return nil, nil, err + } + + copied.Contents.Packages = pl + + if arch != "index" { + // Overwrite single-arch configs with their specific arch. + copied.Archs = []types.Architecture{types.ParseArchitecture(arch)} + } + + ics[arch] = &copied + } + + return ics, missing, nil } type resolved struct { @@ -89,14 +112,22 @@ provided map[string]sets.Set[string] } -func unify(originals []string, inputs []resolved) ([]string, map[string][]string, error) { +// unify returns (locked packages (per arch), missing packages (per arch), error) +func unify(originals []string, inputs []resolved) (map[string][]string, map[string][]string, error) { if len(originals) == 0 { - return nil, nil, nil + // If there are no original packages, then we can't really do anything. + // This used to return nil but multi-arch unification assumes we always + // have an "index" entry, even if it's empty, so we return this now. + // Mostly this is to satisfy some tests that have no package inputs. + return map[string][]string{"index": {}}, nil, nil } originalPackages := resolved{ packages: make(sets.Set[string], len(originals)), versions: make(map[string]string, len(originals)), } + + byArch := map[string][]string{} + for _, orig := range originals { name := orig // The function we want from go-apk is private, but these are all the @@ -114,7 +145,7 @@ // architectures. acc := resolved{ packages: inputs[0].packages.Clone(), - versions: inputs[0].versions, + versions: maps.Clone(inputs[0].versions), provided: inputs[0].provided, } for _, next := range inputs[1:] { @@ -207,6 +238,18 @@ pl = append(pl, fmt.Sprintf("%s=%s", pkg, acc.versions[pkg])) } + // "index" is a sentinel value for the intersectino of all architectures. + // This is a reference to the OCI image index we'll be producing with it. + byArch["index"] = pl + + for _, input := range inputs { + pl := make([]string, 0, len(input.packages)) + for _, pkg := range sets.List(input.packages) { + pl = append(pl, fmt.Sprintf("%s=%s", pkg, input.versions[pkg])) + } + byArch[input.arch] = pl + } + // If a particular architecture is missing additional packages from the // locked set that it produced, than warn about those as well. missingByArch := make(map[string][]string, len(inputs)) @@ -217,10 +260,10 @@ } } if len(missingByArch) > 0 { - return pl, missingByArch, nil + return byArch, missingByArch, nil } - return pl, nil, nil + return byArch, nil, nil } // Copied from go-apk's version.go diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/apko-0.20.2/pkg/build/lock_test.go new/apko-0.21.0/pkg/build/lock_test.go --- old/apko-0.20.2/pkg/build/lock_test.go 2024-12-11 01:41:22.000000000 +0100 +++ new/apko-0.21.0/pkg/build/lock_test.go 2024-12-11 23:02:06.000000000 +0100 @@ -27,15 +27,17 @@ name string originals []string inputs []resolved - want []string + want map[string][]string wantMissing map[string][]string wantDiag error }{{ name: "empty", + want: map[string][]string{"index": {}}, }, { name: "simple single arch", originals: []string{"foo", "bar", "baz"}, inputs: []resolved{{ + arch: "amd64", packages: sets.New("foo", "bar", "baz"), versions: map[string]string{ "foo": "1.2.3", @@ -43,15 +45,23 @@ "baz": "0.0.1", }, }}, - want: []string{ - "bar=2.4.6", - "baz=0.0.1", - "foo=1.2.3", + want: map[string][]string{ + "amd64": { + "bar=2.4.6", + "baz=0.0.1", + "foo=1.2.3", + }, + "index": { + "bar=2.4.6", + "baz=0.0.1", + "foo=1.2.3", + }, }, }, { name: "locked versions", originals: []string{"foo=1.2.3", "bar=2.4.6", "baz=0.0.1"}, inputs: []resolved{{ + arch: "amd64", packages: sets.New("foo", "bar", "baz"), versions: map[string]string{ "foo": "1.2.3", @@ -59,15 +69,23 @@ "baz": "0.0.1", }, }}, - want: []string{ - "bar=2.4.6", - "baz=0.0.1", - "foo=1.2.3", + want: map[string][]string{ + "amd64": { + "bar=2.4.6", + "baz=0.0.1", + "foo=1.2.3", + }, + "index": { + "bar=2.4.6", + "baz=0.0.1", + "foo=1.2.3", + }, }, }, { name: "transitive dependency", originals: []string{"foo", "bar", "baz"}, inputs: []resolved{{ + arch: "amd64", packages: sets.New("foo", "bar", "baz", "bonus"), versions: map[string]string{ "foo": "1.2.3", @@ -76,11 +94,19 @@ "bonus": "5.4.3", }, }}, - want: []string{ - "bar=2.4.6", - "baz=0.0.1", - "bonus=5.4.3", - "foo=1.2.3", + want: map[string][]string{ + "amd64": { + "bar=2.4.6", + "baz=0.0.1", + "bonus=5.4.3", + "foo=1.2.3", + }, + "index": { + "bar=2.4.6", + "baz=0.0.1", + "bonus=5.4.3", + "foo=1.2.3", + }, }, }, { name: "multiple matching architectures", @@ -112,11 +138,25 @@ "bar": sets.New("def", "ogg"), }, }}, - want: []string{ - "bar=2.4.6", - "baz=0.0.1", - "bonus=5.4.3", - "foo=1.2.3", + want: map[string][]string{ + "amd64": { + "bar=2.4.6", + "baz=0.0.1", + "bonus=5.4.3", + "foo=1.2.3", + }, + "arm64": { + "bar=2.4.6", + "baz=0.0.1", + "bonus=5.4.3", + "foo=1.2.3", + }, + "index": { + "bar=2.4.6", + "baz=0.0.1", + "bonus=5.4.3", + "foo=1.2.3", + }, }, }, { name: "mismatched transitive dependency", @@ -140,10 +180,24 @@ "bonus": "5.4.3-r1", }, }}, - want: []string{ - "bar=2.4.6", - "baz=0.0.1", - "foo=1.2.3", + want: map[string][]string{ + "amd64": { + "bar=2.4.6", + "baz=0.0.1", + "bonus=5.4.3-r0", + "foo=1.2.3", + }, + "arm64": { + "bar=2.4.6", + "baz=0.0.1", + "bonus=5.4.3-r1", + "foo=1.2.3", + }, + "index": { + "bar=2.4.6", + "baz=0.0.1", + "foo=1.2.3", + }, }, wantMissing: map[string][]string{ "amd64": {"bonus"}, @@ -175,10 +229,22 @@ "bonus": sets.New("bar"), }, }}, - want: []string{ - "baz=0.0.1", - "bonus=5.4.3", - "foo=1.2.3", + want: map[string][]string{ + "amd64": { + "baz=0.0.1", + "bonus=5.4.3", + "foo=1.2.3", + }, + "arm64": { + "baz=0.0.1", + "bonus=5.4.3", + "foo=1.2.3", + }, + "index": { + "baz=0.0.1", + "bonus=5.4.3", + "foo=1.2.3", + }, }, }, { name: "mismatched direct dependency", @@ -202,7 +268,7 @@ "bonus": "5.4.3", }, }}, - wantDiag: errors.New("unable to lock packages to a consistent version: map[bar:[ (amd64) 2.4.6-r1 (arm64)]]"), + wantDiag: errors.New("unable to lock packages to a consistent version: map[bar:[2.4.6-r0 (amd64) 2.4.6-r1 (arm64)]]"), }, { name: "mismatched direct dependency (with constraint)", originals: []string{"foo", "bar>2.4.6", "baz"}, @@ -231,7 +297,7 @@ // "bonus=5.4.3", // "foo=1.2.3", // }, - wantDiag: errors.New("unable to lock packages to a consistent version: map[bar:[ (amd64) 2.4.6-r1 (arm64)]]"), + wantDiag: errors.New("unable to lock packages to a consistent version: map[bar:[2.4.6-r0 (amd64) 2.4.6-r1 (arm64)]]"), }, { name: "single-architecture resolved dependency", originals: []string{"foo", "bar", "baz"}, @@ -254,10 +320,24 @@ "arm-energy-efficient-as-f-arithmetic": "9.8.7", }, }}, - want: []string{ - "bar=2.4.6", - "baz=0.0.1", - "foo=1.2.3", + want: map[string][]string{ + "amd64": { + "bar=2.4.6", + "baz=0.0.1", + "foo=1.2.3", + "intel-fast-as-f-math=5.4.3", + }, + "arm64": { + "arm-energy-efficient-as-f-arithmetic=9.8.7", + "bar=2.4.6", + "baz=0.0.1", + "foo=1.2.3", + }, + "index": { + "bar=2.4.6", + "baz=0.0.1", + "foo=1.2.3", + }, }, wantMissing: map[string][]string{ "amd64": {"intel-fast-as-f-math"}, ++++++ apko.obsinfo ++++++ --- /var/tmp/diff_new_pack.moqDIz/_old 2024-12-12 21:19:27.623889631 +0100 +++ /var/tmp/diff_new_pack.moqDIz/_new 2024-12-12 21:19:27.627889797 +0100 @@ -1,5 +1,5 @@ name: apko -version: 0.20.2 -mtime: 1733877682 -commit: c26998241454be4057bc100ce1062aaabd9bb944 +version: 0.21.0 +mtime: 1733954526 +commit: d45b6da444f211f49e25d25d26cc0241023d22c8 ++++++ vendor.tar.gz ++++++ /work/SRC/openSUSE:Factory/apko/vendor.tar.gz /work/SRC/openSUSE:Factory/.apko.new.29675/vendor.tar.gz differ: char 5, line 1