Script 'mail_helper' called by obssrc Hello community, here is the log from the commit of package melange for openSUSE:Factory checked in at 2024-02-25 14:06:30 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/melange (Old) and /work/SRC/openSUSE:Factory/.melange.new.1770 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "melange" Sun Feb 25 14:06:30 2024 rev:15 rq:1150102 version:0.6.4 Changes: -------- --- /work/SRC/openSUSE:Factory/melange/melange.changes 2024-02-22 20:58:17.098658077 +0100 +++ /work/SRC/openSUSE:Factory/.melange.new.1770/melange.changes 2024-02-25 14:06:47.790371177 +0100 @@ -1,0 +2,13 @@ +Sat Feb 24 09:01:37 UTC 2024 - [email protected] + +- Update to version 0.6.4: + * Fix the yaml file so that it actually gets parsed properly. + * Propagate SourceDateEpoch from Build + +------------------------------------------------------------------- +Sat Feb 24 08:57:02 UTC 2024 - [email protected] + +- Update to version 0.6.3: + * Don't write APK to temp file during signing + +------------------------------------------------------------------- Old: ---- melange-0.6.2.obscpio New: ---- melange-0.6.4.obscpio ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ melange.spec ++++++ --- /var/tmp/diff_new_pack.q8pojt/_old 2024-02-25 14:06:48.478396082 +0100 +++ /var/tmp/diff_new_pack.q8pojt/_new 2024-02-25 14:06:48.482396226 +0100 @@ -19,7 +19,7 @@ %define __arch_install_post export NO_BRP_STRIP_DEBUG=true Name: melange -Version: 0.6.2 +Version: 0.6.4 Release: 0 Summary: Build APKs from source code License: Apache-2.0 ++++++ _service ++++++ --- /var/tmp/diff_new_pack.q8pojt/_old 2024-02-25 14:06:48.514397385 +0100 +++ /var/tmp/diff_new_pack.q8pojt/_new 2024-02-25 14:06:48.518397530 +0100 @@ -3,7 +3,7 @@ <param name="url">https://github.com/chainguard-dev/melange</param> <param name="scm">git</param> <param name="exclude">.git</param> - <param name="revision">v0.6.2</param> + <param name="revision">v0.6.4</param> <param name="versionformat">@PARENT_TAG@</param> <param name="changesgenerate">enable</param> <param name="versionrewrite-pattern">v(.*)</param> ++++++ _servicedata ++++++ --- /var/tmp/diff_new_pack.q8pojt/_old 2024-02-25 14:06:48.542398398 +0100 +++ /var/tmp/diff_new_pack.q8pojt/_new 2024-02-25 14:06:48.542398398 +0100 @@ -1,6 +1,6 @@ <servicedata> <service name="tar_scm"> <param name="url">https://github.com/chainguard-dev/melange</param> - <param name="changesrevision">e957ab1c612bc7d3a3d7d55d191368151923275f</param></service></servicedata> + <param name="changesrevision">49264c764db801371d44023b72bdaa9d5c2c4174</param></service></servicedata> (No newline at EOF) ++++++ melange-0.6.2.obscpio -> melange-0.6.4.obscpio ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/melange-0.6.2/pkg/build/build.go new/melange-0.6.4/pkg/build/build.go --- old/melange-0.6.2/pkg/build/build.go 2024-02-20 17:12:49.000000000 +0100 +++ new/melange-0.6.4/pkg/build/build.go 2024-02-24 03:43:46.000000000 +0100 @@ -26,6 +26,7 @@ "os" "path/filepath" "runtime" + "strconv" "strings" "time" @@ -47,7 +48,6 @@ "chainguard.dev/melange/pkg/index" "chainguard.dev/melange/pkg/linter" "chainguard.dev/melange/pkg/sbom" - "chainguard.dev/melange/pkg/util" ) var ErrSkipThisArch = errors.New("error: skip this arch") @@ -179,7 +179,7 @@ // SOURCE_DATE_EPOCH will always overwrite the build flag if _, ok := os.LookupEnv("SOURCE_DATE_EPOCH"); ok { - t, err := util.SourceDateEpoch(b.SourceDateEpoch) + t, err := sourceDateEpoch(b.SourceDateEpoch) if err != nil { return nil, err } @@ -835,26 +835,28 @@ } if err := generator.GenerateSBOM(ctx, &sbom.Spec{ - Path: filepath.Join(b.WorkspaceDir, "melange-out", sp.Name), - PackageName: sp.Name, - PackageVersion: fmt.Sprintf("%s-r%d", b.Configuration.Package.Version, b.Configuration.Package.Epoch), - License: b.Configuration.Package.LicenseExpression(), - Copyright: b.Configuration.Package.FullCopyright(), - Namespace: namespace, - Arch: b.Arch.ToAPK(), + Path: filepath.Join(b.WorkspaceDir, "melange-out", sp.Name), + PackageName: sp.Name, + PackageVersion: fmt.Sprintf("%s-r%d", b.Configuration.Package.Version, b.Configuration.Package.Epoch), + License: b.Configuration.Package.LicenseExpression(), + Copyright: b.Configuration.Package.FullCopyright(), + Namespace: namespace, + Arch: b.Arch.ToAPK(), + SourceDateEpoch: b.SourceDateEpoch, }); err != nil { return fmt.Errorf("writing SBOMs: %w", err) } } if err := generator.GenerateSBOM(ctx, &sbom.Spec{ - Path: filepath.Join(b.WorkspaceDir, "melange-out", b.Configuration.Package.Name), - PackageName: b.Configuration.Package.Name, - PackageVersion: fmt.Sprintf("%s-r%d", b.Configuration.Package.Version, b.Configuration.Package.Epoch), - License: b.Configuration.Package.LicenseExpression(), - Copyright: b.Configuration.Package.FullCopyright(), - Namespace: namespace, - Arch: b.Arch.ToAPK(), + Path: filepath.Join(b.WorkspaceDir, "melange-out", b.Configuration.Package.Name), + PackageName: b.Configuration.Package.Name, + PackageVersion: fmt.Sprintf("%s-r%d", b.Configuration.Package.Version, b.Configuration.Package.Epoch), + License: b.Configuration.Package.LicenseExpression(), + Copyright: b.Configuration.Package.FullCopyright(), + Namespace: namespace, + Arch: b.Arch.ToAPK(), + SourceDateEpoch: b.SourceDateEpoch, }); err != nil { return fmt.Errorf("writing SBOMs: %w", err) } @@ -1141,3 +1143,27 @@ return nil } + +// sourceDateEpoch parses the SOURCE_DATE_EPOCH environment variable. +// If it is not set, it returns the defaultTime. +// If it is set, it MUST be an ASCII representation of an integer. +// If it is malformed, it returns an error. +func sourceDateEpoch(defaultTime time.Time) (time.Time, error) { + v := strings.TrimSpace(os.Getenv("SOURCE_DATE_EPOCH")) + if v == "" { + clog.DefaultLogger().Warnf("SOURCE_DATE_EPOCH is specified but empty, setting it to %v", defaultTime) + return defaultTime, nil + } + + // The value MUST be an ASCII representation of an integer + // with no fractional component, identical to the output + // format of date +%s. + sec, err := strconv.ParseInt(v, 10, 64) + if err != nil { + // If the value is malformed, the build process + // SHOULD exit with a non-zero error code. + return defaultTime, fmt.Errorf("failed to parse SOURCE_DATE_EPOCH: %w", err) + } + + return time.Unix(sec, 0).UTC(), nil +} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/melange-0.6.2/pkg/build/build_test.go new/melange-0.6.4/pkg/build/build_test.go --- old/melange-0.6.2/pkg/build/build_test.go 2024-02-20 17:12:49.000000000 +0100 +++ new/melange-0.6.4/pkg/build/build_test.go 2024-02-24 03:43:46.000000000 +0100 @@ -19,6 +19,7 @@ "os" "path/filepath" "testing" + "time" "chainguard.dev/melange/pkg/config" @@ -306,3 +307,65 @@ t.Fatalf("actual didn't match expected: %s", d) } } + +func TestSourceDateEpoch(t *testing.T) { + tests := []struct { + name string + sourceDateEpoch string + defaultTime time.Time + want time.Time + wantErr bool + }{ + { + name: "empty", + defaultTime: time.Time{}, + want: time.Time{}, + }, + { + name: "strings", + sourceDateEpoch: " ", + defaultTime: time.Time{}, + want: time.Time{}, + }, + { + name: "defaultTime", + defaultTime: time.Unix(1234567890, 0), + want: time.Unix(1234567890, 0), + }, + { + name: "0", + sourceDateEpoch: "0", + defaultTime: time.Unix(1234567890, 0), + want: time.Unix(0, 0), + }, + { + name: "1234567890", + sourceDateEpoch: "1234567890", + defaultTime: time.Unix(0, 0), + want: time.Unix(1234567890, 0), + }, + { + name: "invalid date", + sourceDateEpoch: "tacocat", + defaultTime: time.Unix(0, 0), + wantErr: true, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + if tt.sourceDateEpoch != "" { + t.Setenv("SOURCE_DATE_EPOCH", tt.sourceDateEpoch) + } + got, err := sourceDateEpoch(tt.defaultTime) + if err != nil { + if !tt.wantErr { + t.Fatalf("SourceDateEpoch() error = %v, wantErr %v", err, tt.wantErr) + } + return + } + if !got.Equal(tt.want) { + t.Errorf("SourceDateEpoch() = %v, want %v", got, tt.want) + } + }) + } +} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/melange-0.6.2/pkg/build/pipelines/python/import.yaml new/melange-0.6.4/pkg/build/pipelines/python/import.yaml --- old/melange-0.6.2/pkg/build/pipelines/python/import.yaml 2024-02-20 17:12:49.000000000 +0100 +++ new/melange-0.6.4/pkg/build/pipelines/python/import.yaml 2024-02-24 03:43:46.000000000 +0100 @@ -1,4 +1,4 @@ - name: Test a python package import, with optional from clause +name: Test a python package import, with optional from clause needs: packages: diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/melange-0.6.2/pkg/cli/sign.go new/melange-0.6.4/pkg/cli/sign.go --- old/melange-0.6.2/pkg/cli/sign.go 2024-02-20 17:12:49.000000000 +0100 +++ new/melange-0.6.4/pkg/cli/sign.go 2024-02-24 03:43:46.000000000 +0100 @@ -214,6 +214,7 @@ if err != nil { return err } + defer cf.Close() // Use the control sections ModTime (set to SDE) for the signature cfinfo, err := os.Stat(eapk.ControlFile) @@ -242,26 +243,7 @@ if err != nil { return err } - - tf, err := os.CreateTemp("", "melange-signer") - if err != nil { - return err - } - defer os.RemoveAll(tf.Name()) - - for _, fp := range []io.Reader{bytes.NewBuffer(sigData), cf, df} { - if _, err := io.Copy(tf, fp); err != nil { - return err - } - } - - if err := tf.Sync(); err != nil { - return err - } - - if _, err := tf.Seek(0, io.SeekStart); err != nil { - return err - } + defer df.Close() // Replace the package file with the new one f, err := os.Create(pkg) @@ -270,8 +252,10 @@ } defer f.Close() - if _, err := io.Copy(f, tf); err != nil { - return err + for _, fp := range []io.Reader{bytes.NewBuffer(sigData), cf, df} { + if _, err := io.Copy(f, fp); err != nil { + return err + } } return nil diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/melange-0.6.2/pkg/sbom/generator.go new/melange-0.6.4/pkg/sbom/generator.go --- old/melange-0.6.2/pkg/sbom/generator.go 2024-02-20 17:12:49.000000000 +0100 +++ new/melange-0.6.4/pkg/sbom/generator.go 2024-02-24 03:43:46.000000000 +0100 @@ -17,6 +17,7 @@ import ( "context" "fmt" + "time" "github.com/chainguard-dev/clog" "go.opentelemetry.io/otel" @@ -27,13 +28,14 @@ } type Spec struct { - Path string - PackageName string - PackageVersion string - License string // Full SPDX license expression - Copyright string - Namespace string - Arch string + Path string + PackageName string + PackageVersion string + License string // Full SPDX license expression + Copyright string + Namespace string + Arch string + SourceDateEpoch time.Time } type Generator struct{} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/melange-0.6.2/pkg/sbom/implementation.go new/melange-0.6.4/pkg/sbom/implementation.go --- old/melange-0.6.2/pkg/sbom/implementation.go 2024-02-20 17:12:49.000000000 +0100 +++ new/melange-0.6.4/pkg/sbom/implementation.go 2024-02-24 03:43:46.000000000 +0100 @@ -44,7 +44,6 @@ "sigs.k8s.io/release-utils/version" "chainguard.dev/apko/pkg/sbom/generator/spdx" - "chainguard.dev/melange/pkg/util" ) var validIDCharsRe = regexp.MustCompile(`[^a-zA-Z0-9-.]+`) @@ -339,12 +338,6 @@ func buildDocumentSPDX(ctx context.Context, spec *Spec, doc *bom) (*spdx.Document, error) { log := clog.FromContext(ctx) - // Build the SBOM time, but respect SOURCE_DATE_EPOCH - sbomTime, err := util.SourceDateEpoch(time.Now().UTC()) - if err != nil { - return nil, err - } - h := sha1.New() h.Write([]byte(fmt.Sprintf("apk-%s-%s", spec.PackageName, spec.PackageVersion))) @@ -353,7 +346,7 @@ Name: fmt.Sprintf("apk-%s-%s", spec.PackageName, spec.PackageVersion), Version: "SPDX-2.3", CreationInfo: spdx.CreationInfo{ - Created: sbomTime.Format(time.RFC3339), + Created: spec.SourceDateEpoch.Format(time.RFC3339), Creators: []string{ fmt.Sprintf("Tool: melange (%s)", version.GetVersionInfo().GitVersion), "Organization: Chainguard, Inc", diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/melange-0.6.2/pkg/util/env.go new/melange-0.6.4/pkg/util/env.go --- old/melange-0.6.2/pkg/util/env.go 2024-02-20 17:12:49.000000000 +0100 +++ new/melange-0.6.4/pkg/util/env.go 1970-01-01 01:00:00.000000000 +0100 @@ -1,48 +0,0 @@ -// Copyright 2023 Chainguard, Inc. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -package util - -import ( - "fmt" - "os" - "strconv" - "strings" - "time" - - "github.com/chainguard-dev/clog" -) - -// SourceDateEpoch parses the SOURCE_DATE_EPOCH environment variable. -// If it is not set, it returns the defaultTime. -// If it is set, it MUST be an ASCII representation of an integer. -// If it is malformed, it returns an error. -func SourceDateEpoch(defaultTime time.Time) (time.Time, error) { - v := strings.TrimSpace(os.Getenv("SOURCE_DATE_EPOCH")) - if v == "" { - clog.DefaultLogger().Warnf("SOURCE_DATE_EPOCH is specified but empty, setting it to %v", defaultTime) - return defaultTime, nil - } - - // The value MUST be an ASCII representation of an integer - // with no fractional component, identical to the output - // format of date +%s. - sec, err := strconv.ParseInt(v, 10, 64) - if err != nil { - // If the value is malformed, the build process - // SHOULD exit with a non-zero error code. - return defaultTime, fmt.Errorf("failed to parse SOURCE_DATE_EPOCH: %w", err) - } - - return time.Unix(sec, 0).UTC(), nil -} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/melange-0.6.2/pkg/util/env_test.go new/melange-0.6.4/pkg/util/env_test.go --- old/melange-0.6.2/pkg/util/env_test.go 2024-02-20 17:12:49.000000000 +0100 +++ new/melange-0.6.4/pkg/util/env_test.go 1970-01-01 01:00:00.000000000 +0100 @@ -1,81 +0,0 @@ -// Copyright 2023 Chainguard, Inc. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -package util - -import ( - "testing" - "time" -) - -func TestSourceDateEpoch(t *testing.T) { - tests := []struct { - name string - sourceDateEpoch string - defaultTime time.Time - want time.Time - wantErr bool - }{ - { - name: "empty", - defaultTime: time.Time{}, - want: time.Time{}, - }, - { - name: "strings", - sourceDateEpoch: " ", - defaultTime: time.Time{}, - want: time.Time{}, - }, - { - name: "defaultTime", - defaultTime: time.Unix(1234567890, 0), - want: time.Unix(1234567890, 0), - }, - { - name: "0", - sourceDateEpoch: "0", - defaultTime: time.Unix(1234567890, 0), - want: time.Unix(0, 0), - }, - { - name: "1234567890", - sourceDateEpoch: "1234567890", - defaultTime: time.Unix(0, 0), - want: time.Unix(1234567890, 0), - }, - { - name: "invalid date", - sourceDateEpoch: "tacocat", - defaultTime: time.Unix(0, 0), - wantErr: true, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - if tt.sourceDateEpoch != "" { - t.Setenv("SOURCE_DATE_EPOCH", tt.sourceDateEpoch) - } - got, err := SourceDateEpoch(tt.defaultTime) - if err != nil { - if !tt.wantErr { - t.Fatalf("SourceDateEpoch() error = %v, wantErr %v", err, tt.wantErr) - } - return - } - if !got.Equal(tt.want) { - t.Errorf("SourceDateEpoch() = %v, want %v", got, tt.want) - } - }) - } -} ++++++ melange.obsinfo ++++++ --- /var/tmp/diff_new_pack.q8pojt/_old 2024-02-25 14:06:48.846409403 +0100 +++ /var/tmp/diff_new_pack.q8pojt/_new 2024-02-25 14:06:48.846409403 +0100 @@ -1,5 +1,5 @@ name: melange -version: 0.6.2 -mtime: 1708445569 -commit: e957ab1c612bc7d3a3d7d55d191368151923275f +version: 0.6.4 +mtime: 1708742626 +commit: 49264c764db801371d44023b72bdaa9d5c2c4174 ++++++ vendor.tar.gz ++++++ /work/SRC/openSUSE:Factory/melange/vendor.tar.gz /work/SRC/openSUSE:Factory/.melange.new.1770/vendor.tar.gz differ: char 5, line 1
