From 83adc3c8904d2fc74b2918f17ed6cc7aabbc19ff Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 29 May 2026 17:25:42 +0000 Subject: [PATCH] Implement signature-lint cleanup and fix lint formatting --- pkg/extensions/extensions_lint.go | 1 - pkg/extensions/lint/lint.go | 5 ++- pkg/extensions/lint/lint_signatures_test.go | 2 -- pkg/storage/imagestore/imagestore.go | 11 ++++++ pkg/storage/storage_test.go | 38 +++++++++++++++++++++ 5 files changed, 53 insertions(+), 4 deletions(-) diff --git a/pkg/extensions/extensions_lint.go b/pkg/extensions/extensions_lint.go index c47f1c84..14418477 100644 --- a/pkg/extensions/extensions_lint.go +++ b/pkg/extensions/extensions_lint.go @@ -82,7 +82,6 @@ func containsFiles(root string) bool { return nil }) - if walkErr != nil { return false } diff --git a/pkg/extensions/lint/lint.go b/pkg/extensions/lint/lint.go index 1888a273..ed3e0818 100644 --- a/pkg/extensions/lint/lint.go +++ b/pkg/extensions/lint/lint.go @@ -134,6 +134,7 @@ func (linter *Linter) CheckMandatorySignatures(repo string, manifestDigest godig } mandatory := false + for _, mandatoryRepo := range linter.config.MandatorySignatures { if mandatoryRepo == "*" || mandatoryRepo == "**" || repo == mandatoryRepo { mandatory = true @@ -228,7 +229,9 @@ func (linter *Linter) hasTrustedSignature(repo string, manifestDigest godigest.D return false, nil } -func getSignatureType(descriptor ispec.Descriptor, signatureManifest ispec.Manifest, manifestDigest godigest.Digest) (string, bool) { +func getSignatureType(descriptor ispec.Descriptor, signatureManifest ispec.Manifest, + manifestDigest godigest.Digest, +) (string, bool) { artifactType := zcommon.GetManifestArtifactType(signatureManifest) if signatureManifest.Subject != nil && signatureManifest.Subject.Digest == manifestDigest { diff --git a/pkg/extensions/lint/lint_signatures_test.go b/pkg/extensions/lint/lint_signatures_test.go index 608330ef..49881f7f 100644 --- a/pkg/extensions/lint/lint_signatures_test.go +++ b/pkg/extensions/lint/lint_signatures_test.go @@ -113,8 +113,6 @@ func TestMandatorySignaturesFunction(t *testing.T) { }) for _, wildcard := range []string{"*", "**"} { - wildcard := wildcard - Convey("mandatory signatures check rejects unsigned images for wildcard repository list "+wildcard, t, func() { enable := true lintConfig := &extconf.LintConfig{ diff --git a/pkg/storage/imagestore/imagestore.go b/pkg/storage/imagestore/imagestore.go index 4538e40e..97bdaa94 100644 --- a/pkg/storage/imagestore/imagestore.go +++ b/pkg/storage/imagestore/imagestore.go @@ -638,6 +638,8 @@ func (is *ImageStore) PutImageManifest(repo, reference, mediaType string, //noli manifestPath := path.Join(dir, mDigest.Encoded()) binfo, err := is.storeDriver.Stat(manifestPath) + manifestUploaded := false + if err != nil || binfo.Size() != desc.Size { // The blob isn't already there, or it is corrupted, and needs a correction if _, err = is.storeDriver.WriteFile(manifestPath, body); err != nil { @@ -645,6 +647,8 @@ func (is *ImageStore) PutImageManifest(repo, reference, mediaType string, //noli return "", "", err } + + manifestUploaded = true } var ( @@ -761,6 +765,13 @@ func (is *ImageStore) PutImageManifest(repo, reference, mediaType string, //noli is.log.Error().Err(err).Str("repository", repo).Str("reference", reference). Msg("linter didn't pass") + if manifestUploaded && zerr.GetDetails(err)["missingSignatures"] != "" { + if deleteErr := is.storeDriver.Delete(manifestPath); deleteErr != nil { + is.log.Error().Err(deleteErr).Str("repository", repo).Str("reference", reference). + Str("digest", mDigest.String()).Msg("failed to delete untrusted manifest") + } + } + if is.events != nil { is.events.ImageLintFailed(repo, reference, mDigest.String(), mediaType, string(body)) } diff --git a/pkg/storage/storage_test.go b/pkg/storage/storage_test.go index e9c891d2..712be086 100644 --- a/pkg/storage/storage_test.go +++ b/pkg/storage/storage_test.go @@ -1492,12 +1492,50 @@ func TestMandatoryAnnotations(t *testing.T) { manifest.SchemaVersion = 2 manifestBuf, err := json.Marshal(manifest) So(err, ShouldBeNil) + manifestDigest := godigest.FromBytes(manifestBuf) Convey("Missing mandatory annotations", func() { _, _, err = imgStore.PutImageManifest("test", "1.0.0", ispec.MediaTypeImageManifest, manifestBuf, nil) So(err, ShouldNotBeNil) }) + Convey("Signature lint failure deletes uploaded manifest blob and does not update index", func() { + if testcase.storageType == storageConstants.S3StorageDriverName { + imgStore = imagestore.NewImageStore(testDir, cacheDir, false, false, log, metrics, + &mocks.MockedLint{ + LintFn: func(repo string, manifestDigest godigest.Digest, + imageStore storageTypes.ImageStore, + ) (bool, error) { + return false, zerr.NewError(zerr.ErrImageLintAnnotations). + AddDetail("missingSignatures", "missing trusted signature") + }, + }, store, nil, nil, nil) + } else { + var cacheDriver storageTypes.Cache + store, _, cacheDriver, err := createObjectsStore(opts) + So(err, ShouldBeNil) + imgStore = imagestore.NewImageStore(cacheDir, cacheDir, true, true, log, metrics, + &mocks.MockedLint{ + LintFn: func(repo string, manifestDigest godigest.Digest, + imageStore storageTypes.ImageStore, + ) (bool, error) { + return false, zerr.NewError(zerr.ErrImageLintAnnotations). + AddDetail("missingSignatures", "missing trusted signature") + }, + }, store, cacheDriver, nil, nil) + } + + _, _, err = imgStore.PutImageManifest("test", "1.0.0", ispec.MediaTypeImageManifest, manifestBuf, nil) + So(err, ShouldNotBeNil) + + _, err = imgStore.GetBlobContent("test", manifestDigest) + So(err, ShouldEqual, zerr.ErrBlobNotFound) + + index, err := storageCommon.GetIndex(imgStore, "test", log) + So(err, ShouldBeNil) + So(len(index.Manifests), ShouldEqual, 0) + }) + Convey("Error on mandatory annotations", func() { if testcase.storageType == storageConstants.S3StorageDriverName { imgStore = imagestore.NewImageStore(testDir, cacheDir, false, false, log, metrics,