pull/32403/merge
Amariah Abishai 2 months ago committed by GitHub
commit bc3badf719
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -17,10 +17,18 @@ limitations under the License.
package action
import (
"archive/tar"
"bytes"
"compress/gzip"
"errors"
"io"
"os"
"path"
"strings"
"testing"
"time"
"sigs.k8s.io/yaml"
"github.com/Masterminds/semver/v3"
"github.com/stretchr/testify/assert"
@ -170,3 +178,69 @@ func TestRun(t *testing.T) {
require.Equal(t, "empty-0.1.0.tgz", filename)
require.NoError(t, os.Remove(filename))
}
func TestRunWithSourceDateEpochAndLock(t *testing.T) {
tmp := t.TempDir()
epoch := time.Unix(1609459200, 0).UTC()
// Build twice with the same SourceDateEpoch and assert byte-identical output.
var first []byte
for i := range 2 {
client := NewPackage()
client.Destination = tmp
client.SourceDateEpoch = &epoch
dest, err := client.Run("testdata/charts/chart-with-lock", nil)
require.NoError(t, err)
data, err := os.ReadFile(dest)
require.NoError(t, err)
if i == 0 {
first = data
} else {
require.Equal(t, first, data, "two builds with the same SourceDateEpoch must be byte-identical")
}
require.NoError(t, os.Remove(dest))
}
// Open the archive and inspect Chart.lock content.
gz, err := gzip.NewReader(bytes.NewReader(first))
require.NoError(t, err)
defer gz.Close()
tr := tar.NewReader(gz)
var lockData []byte
var lockHdr *tar.Header
for {
hdr, err := tr.Next()
if errors.Is(err, io.EOF) {
break
}
require.NoError(t, err)
if strings.HasSuffix(hdr.Name, "Chart.lock") {
lockHdr = hdr
var buf bytes.Buffer
_, err := io.Copy(&buf, tr)
require.NoError(t, err)
lockData = buf.Bytes()
break
}
}
require.NotNil(t, lockHdr, "Chart.lock not found in archive")
require.NotNil(t, lockData)
// Validate the generated field in the YAML is the epoch (not the fixture's original timestamp).
var lock struct {
Generated string `yaml:"generated"`
}
err = yaml.Unmarshal(lockData, &lock)
require.NoError(t, err)
require.Equal(t, "2021-01-01T00:00:00Z", lock.Generated,
"Chart.lock generated field must match SourceDateEpoch")
// Tar header ModTime must also match.
require.True(t, lockHdr.ModTime.Equal(epoch),
"Chart.lock tar header ModTime must match SourceDateEpoch: got %v, want %v",
lockHdr.ModTime, epoch)
}

@ -0,0 +1,6 @@
dependencies:
- name: nginx
repository: https://charts.bitnami.com/bitnami
version: 1.0.0
digest: sha256:abc123def456
generated: "2024-01-01T12:00:00Z"

@ -0,0 +1,4 @@
apiVersion: v2
name: chart-with-lock
description: Test chart with Chart.lock for reproducibility testing
version: 0.1.0

@ -0,0 +1 @@
# This file is intentionally blank

@ -180,6 +180,7 @@ func (ch *Chart) CRDObjects() []CRD {
// StampModTimes sets timestamps on the chart (and dependencies) to epoch.
// This is used for reproducible builds via SOURCE_DATE_EPOCH.
func (ch *Chart) StampModTimes(epoch time.Time) {
epoch = epoch.UTC().Truncate(time.Second)
ch.ModTime = epoch
if len(ch.Schema) > 0 {
ch.SchemaModTime = epoch

Loading…
Cancel
Save