diff --git a/pkg/common/common.go b/pkg/common/common.go index 36e20e49..76635a4f 100644 --- a/pkg/common/common.go +++ b/pkg/common/common.go @@ -19,6 +19,10 @@ const ( clientCertFilename = "client.cert" clientKeyFilename = "client.key" caCertFilename = "ca.crt" + + CosignSignature = "cosign" + CosignSigKey = "dev.cosignproject.cosign/signature" + NotationSignature = "notation" ) func Contains[T comparable](elems []T, v T) bool { diff --git a/pkg/extensions/extension_image_trust.go b/pkg/extensions/extension_image_trust.go index 19c41ceb..abf0f0c0 100644 --- a/pkg/extensions/extension_image_trust.go +++ b/pkg/extensions/extension_image_trust.go @@ -15,8 +15,8 @@ import ( "zotregistry.io/zot/pkg/api/config" "zotregistry.io/zot/pkg/api/constants" zcommon "zotregistry.io/zot/pkg/common" + "zotregistry.io/zot/pkg/extensions/imagetrust" "zotregistry.io/zot/pkg/log" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" "zotregistry.io/zot/pkg/scheduler" ) @@ -93,7 +93,7 @@ func (trust *ImageTrust) HandleCosignPublicKeyUpload(response http.ResponseWrite return } - err = signatures.UploadPublicKey(body) + err = imagetrust.UploadPublicKey(body) if err != nil { if errors.Is(err, zerr.ErrInvalidPublicKeyContent) { response.WriteHeader(http.StatusBadRequest) @@ -151,7 +151,7 @@ func (trust *ImageTrust) HandleNotationCertificateUpload(response http.ResponseW return } - err = signatures.UploadCertificate(body, truststoreType, truststoreName) + err = imagetrust.UploadCertificate(body, truststoreType, truststoreName) if err != nil { if errors.Is(err, zerr.ErrInvalidTruststoreType) || errors.Is(err, zerr.ErrInvalidTruststoreName) || @@ -175,7 +175,7 @@ func EnableImageTrustVerification(conf *config.Config, taskScheduler *scheduler. return } - generator := signatures.NewTaskGenerator(metaDB, log) + generator := imagetrust.NewTaskGenerator(metaDB, log) numberOfHours := 2 interval := time.Duration(numberOfHours) * time.Minute diff --git a/pkg/meta/signatures/cosign.go b/pkg/extensions/imagetrust/cosign.go similarity index 95% rename from pkg/meta/signatures/cosign.go rename to pkg/extensions/imagetrust/cosign.go index 85560158..be05955a 100644 --- a/pkg/meta/signatures/cosign.go +++ b/pkg/extensions/imagetrust/cosign.go @@ -1,4 +1,7 @@ -package signatures +//go:build imagetrust +// +build imagetrust + +package imagetrust import ( "bytes" @@ -19,10 +22,7 @@ import ( zerr "zotregistry.io/zot/errors" ) -const ( - CosignSigKey = "dev.cosignproject.cosign/signature" - cosignDirRelativePath = "_cosign" -) +const cosignDirRelativePath = "_cosign" var cosignDir = "" //nolint:gochecknoglobals diff --git a/pkg/meta/signatures/signatures.go b/pkg/extensions/imagetrust/image_trust.go similarity index 91% rename from pkg/meta/signatures/signatures.go rename to pkg/extensions/imagetrust/image_trust.go index 2f07e826..ca4c8f2f 100644 --- a/pkg/meta/signatures/signatures.go +++ b/pkg/extensions/imagetrust/image_trust.go @@ -1,4 +1,7 @@ -package signatures +//go:build imagetrust +// +build imagetrust + +package imagetrust import ( "context" @@ -9,16 +12,15 @@ import ( ispec "github.com/opencontainers/image-spec/specs-go/v1" zerr "zotregistry.io/zot/errors" + zcommon "zotregistry.io/zot/pkg/common" "zotregistry.io/zot/pkg/log" mTypes "zotregistry.io/zot/pkg/meta/types" "zotregistry.io/zot/pkg/scheduler" ) const ( - CosignSignature = "cosign" - NotationSignature = "notation" - defaultDirPerms = 0o700 - defaultFilePerms = 0o644 + defaultDirPerms = 0o700 + defaultFilePerms = 0o644 ) func InitCosignAndNotationDirs(rootDir string) error { @@ -52,11 +54,11 @@ func VerifySignature( } switch signatureType { - case CosignSignature: + case zcommon.CosignSignature: author, isValid, err := VerifyCosignSignature(repo, manifestDigest, sigKey, rawSignature) return author, time.Time{}, isValid, err - case NotationSignature: + case zcommon.NotationSignature: return VerifyNotationSignature(desc, manifestDigest.String(), rawSignature, sigKey) default: return "", time.Time{}, false, zerr.ErrInvalidSignatureType @@ -137,7 +139,7 @@ func (validityT *validityTask) DoWork() error { validityT.log.Info().Msg("updating signatures validity") for signedManifest, sigs := range validityT.repo.Signatures { - if len(sigs[CosignSignature]) != 0 || len(sigs[NotationSignature]) != 0 { + if len(sigs[zcommon.CosignSignature]) != 0 || len(sigs[zcommon.NotationSignature]) != 0 { err := validityT.metaDB.UpdateSignaturesValidity(validityT.repo.Name, godigest.Digest(signedManifest)) if err != nil { validityT.log.Info().Msg("error while verifying signatures") diff --git a/pkg/extensions/imagetrust/image_trust_disabled.go b/pkg/extensions/imagetrust/image_trust_disabled.go new file mode 100644 index 00000000..6a5b9e36 --- /dev/null +++ b/pkg/extensions/imagetrust/image_trust_disabled.go @@ -0,0 +1,29 @@ +//go:build !imagetrust +// +build !imagetrust + +package imagetrust + +import ( + "time" + + godigest "github.com/opencontainers/go-digest" +) + +func InitCosignAndNotationDirs(rootDir string) error { + return nil +} + +func InitCosignDir(rootDir string) error { + return nil +} + +func InitNotationDir(rootDir string) error { + return nil +} + +func VerifySignature( + signatureType string, rawSignature []byte, sigKey string, manifestDigest godigest.Digest, manifestContent []byte, + repo string, +) (string, time.Time, bool, error) { + return "", time.Time{}, false, nil +} diff --git a/pkg/extensions/imagetrust/image_trust_disabled_test.go b/pkg/extensions/imagetrust/image_trust_disabled_test.go new file mode 100644 index 00000000..9f365004 --- /dev/null +++ b/pkg/extensions/imagetrust/image_trust_disabled_test.go @@ -0,0 +1,47 @@ +//go:build !imagetrust + +package imagetrust_test + +import ( + "os" + "path" + "testing" + + . "github.com/smartystreets/goconvey/convey" + + "zotregistry.io/zot/pkg/extensions/imagetrust" +) + +func TestImageTrust(t *testing.T) { + Convey("binary doesn't include imagetrust", t, func() { + rootDir := t.TempDir() + + err := imagetrust.InitCosignDir(rootDir) + So(err, ShouldBeNil) + + cosignDir := path.Join(rootDir, "_cosign") + _, err = os.Stat(cosignDir) + So(os.IsNotExist(err), ShouldBeTrue) + + err = imagetrust.InitNotationDir(rootDir) + So(err, ShouldBeNil) + + notationDir := path.Join(rootDir, "_notation") + _, err = os.Stat(notationDir) + So(os.IsNotExist(err), ShouldBeTrue) + + err = imagetrust.InitCosignAndNotationDirs(rootDir) + So(err, ShouldBeNil) + + _, err = os.Stat(cosignDir) + So(os.IsNotExist(err), ShouldBeTrue) + _, err = os.Stat(notationDir) + So(os.IsNotExist(err), ShouldBeTrue) + + author, expTime, ok, err := imagetrust.VerifySignature("", []byte{}, "", "", []byte{}, "") + So(author, ShouldBeEmpty) + So(expTime, ShouldBeZeroValue) + So(ok, ShouldBeFalse) + So(err, ShouldBeNil) + }) +} diff --git a/pkg/meta/signatures/signatures_test.go b/pkg/extensions/imagetrust/image_trust_test.go similarity index 81% rename from pkg/meta/signatures/signatures_test.go rename to pkg/extensions/imagetrust/image_trust_test.go index 6a711774..4916f9ef 100644 --- a/pkg/meta/signatures/signatures_test.go +++ b/pkg/extensions/imagetrust/image_trust_test.go @@ -1,4 +1,7 @@ -package signatures_test +//go:build imagetrust +// +build imagetrust + +package imagetrust_test import ( "context" @@ -21,7 +24,8 @@ import ( zerr "zotregistry.io/zot/errors" "zotregistry.io/zot/pkg/api" "zotregistry.io/zot/pkg/api/config" - "zotregistry.io/zot/pkg/meta/signatures" + zcommon "zotregistry.io/zot/pkg/common" + "zotregistry.io/zot/pkg/extensions/imagetrust" "zotregistry.io/zot/pkg/test" ) @@ -33,16 +37,16 @@ func TestInitCosignAndNotationDirs(t *testing.T) { err := os.Chmod(dir, 0o000) So(err, ShouldBeNil) - err = signatures.InitCosignAndNotationDirs(dir) + err = imagetrust.InitCosignAndNotationDirs(dir) So(err, ShouldNotBeNil) err = os.Chmod(dir, 0o500) So(err, ShouldBeNil) - err = signatures.InitCosignAndNotationDirs(dir) + err = imagetrust.InitCosignAndNotationDirs(dir) So(err, ShouldNotBeNil) - cosignDir, err := signatures.GetCosignDirPath() + cosignDir, err := imagetrust.GetCosignDirPath() So(cosignDir, ShouldBeEmpty) So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrSignConfigDirNotSet) @@ -53,22 +57,22 @@ func TestInitCosignAndNotationDirs(t *testing.T) { err := os.Chmod(dir, 0o000) So(err, ShouldBeNil) - err = signatures.InitCosignAndNotationDirs(dir) + err = imagetrust.InitCosignAndNotationDirs(dir) So(err, ShouldNotBeNil) - err = signatures.InitNotationDir(dir) + err = imagetrust.InitNotationDir(dir) So(err, ShouldNotBeNil) err = os.Chmod(dir, 0o500) So(err, ShouldBeNil) - err = signatures.InitCosignAndNotationDirs(dir) + err = imagetrust.InitCosignAndNotationDirs(dir) So(err, ShouldNotBeNil) - err = signatures.InitNotationDir(dir) + err = imagetrust.InitNotationDir(dir) So(err, ShouldNotBeNil) - notationDir, err := signatures.GetNotationDirPath() + notationDir, err := imagetrust.GetNotationDirPath() So(notationDir, ShouldBeEmpty) So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrSignConfigDirNotSet) @@ -90,7 +94,7 @@ func TestInitCosignAndNotationDirs(t *testing.T) { So(err, ShouldBeNil) So(certificateContent, ShouldNotBeNil) - err = signatures.UploadCertificate(certificateContent, "ca", "notation-upload-test") + err = imagetrust.UploadCertificate(certificateContent, "ca", "notation-upload-test") So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrSignConfigDirNotSet) }) @@ -114,7 +118,7 @@ func TestInitCosignAndNotationDirs(t *testing.T) { So(err, ShouldBeNil) So(publicKeyContent, ShouldNotBeNil) - err = signatures.UploadPublicKey(publicKeyContent) + err = imagetrust.UploadPublicKey(publicKeyContent) So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrSignConfigDirNotSet) }) @@ -124,7 +128,7 @@ func TestVerifySignatures(t *testing.T) { Convey("wrong manifest content", t, func() { manifestContent := []byte("wrong json") - _, _, _, err := signatures.VerifySignature("", []byte(""), "", "", manifestContent, "repo") + _, _, _, err := imagetrust.VerifySignature("", []byte(""), "", "", manifestContent, "repo") So(err, ShouldNotBeNil) }) @@ -135,7 +139,7 @@ func TestVerifySignatures(t *testing.T) { manifestContent, err := json.Marshal(image.Manifest) So(err, ShouldBeNil) - _, _, _, err = signatures.VerifySignature("", []byte(""), "", "", manifestContent, "repo") + _, _, _, err = imagetrust.VerifySignature("", []byte(""), "", "", manifestContent, "repo") So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrBadManifestDigest) }) @@ -149,7 +153,7 @@ func TestVerifySignatures(t *testing.T) { manifestDigest := image.Digest() - _, _, _, err = signatures.VerifySignature("wrongType", []byte(""), "", manifestDigest, manifestContent, "repo") + _, _, _, err = imagetrust.VerifySignature("wrongType", []byte(""), "", manifestDigest, manifestContent, "repo") So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrInvalidSignatureType) }) @@ -166,7 +170,7 @@ func TestVerifySignatures(t *testing.T) { manifestDigest := image.Digest() Convey("cosignDir is not set", func() { - _, _, _, err = signatures.VerifySignature("cosign", []byte(""), "", manifestDigest, manifestContent, repo) + _, _, _, err = imagetrust.VerifySignature("cosign", []byte(""), "", manifestDigest, manifestContent, repo) So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrSignConfigDirNotSet) }) @@ -174,31 +178,31 @@ func TestVerifySignatures(t *testing.T) { Convey("cosignDir does not have read permissions", func() { dir := t.TempDir() - err := signatures.InitCosignDir(dir) + err := imagetrust.InitCosignDir(dir) So(err, ShouldBeNil) - cosignDir, err := signatures.GetCosignDirPath() + cosignDir, err := imagetrust.GetCosignDirPath() So(err, ShouldBeNil) err = os.Chmod(cosignDir, 0o300) So(err, ShouldBeNil) - _, _, _, err = signatures.VerifySignature("cosign", []byte(""), "", manifestDigest, manifestContent, repo) + _, _, _, err = imagetrust.VerifySignature("cosign", []byte(""), "", manifestDigest, manifestContent, repo) So(err, ShouldNotBeNil) }) Convey("no valid public key", func() { dir := t.TempDir() - err := signatures.InitCosignDir(dir) + err := imagetrust.InitCosignDir(dir) So(err, ShouldBeNil) - cosignDir, err := signatures.GetCosignDirPath() + cosignDir, err := imagetrust.GetCosignDirPath() So(err, ShouldBeNil) err = test.WriteFileWithPermission(path.Join(cosignDir, "file"), []byte("not a public key"), 0o600, false) So(err, ShouldBeNil) - _, _, isTrusted, err := signatures.VerifySignature("cosign", []byte(""), "", manifestDigest, manifestContent, repo) + _, _, isTrusted, err := imagetrust.VerifySignature("cosign", []byte(""), "", manifestDigest, manifestContent, repo) So(err, ShouldBeNil) So(isTrusted, ShouldBeFalse) }) @@ -221,10 +225,10 @@ func TestVerifySignatures(t *testing.T) { err := test.UploadImage(image, baseURL, repo, tag) So(err, ShouldBeNil) - err = signatures.InitCosignDir(rootDir) + err = imagetrust.InitCosignDir(rootDir) So(err, ShouldBeNil) - cosignDir, err := signatures.GetCosignDirPath() + cosignDir, err := imagetrust.GetCosignDirPath() So(err, ShouldBeNil) cwd, err := os.Getwd() @@ -273,7 +277,7 @@ func TestVerifySignatures(t *testing.T) { err = json.Unmarshal(blobContent, &cosignSig) So(err, ShouldBeNil) - sigKey = cosignSig.Layers[0].Annotations[signatures.CosignSigKey] + sigKey = cosignSig.Layers[0].Annotations[zcommon.CosignSigKey] rawSignature, err = ctlr.StoreController.DefaultStore.GetBlobContent(repo, cosignSig.Layers[0].Digest) So(err, ShouldBeNil) @@ -281,7 +285,7 @@ func TestVerifySignatures(t *testing.T) { } // signature is trusted - author, _, isTrusted, err := signatures.VerifySignature("cosign", rawSignature, sigKey, manifestDigest, + author, _, isTrusted, err := imagetrust.VerifySignature("cosign", rawSignature, sigKey, manifestDigest, manifestContent, repo) So(err, ShouldBeNil) So(isTrusted, ShouldBeTrue) @@ -301,7 +305,7 @@ func TestVerifySignatures(t *testing.T) { manifestDigest := image.Digest() Convey("notationDir is not set", func() { - _, _, _, err = signatures.VerifySignature("notation", []byte("signature"), "", manifestDigest, manifestContent, repo) + _, _, _, err = imagetrust.VerifySignature("notation", []byte("signature"), "", manifestDigest, manifestContent, repo) So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrSignConfigDirNotSet) }) @@ -309,10 +313,10 @@ func TestVerifySignatures(t *testing.T) { Convey("no signature provided", func() { dir := t.TempDir() - err := signatures.InitNotationDir(dir) + err := imagetrust.InitNotationDir(dir) So(err, ShouldBeNil) - _, _, isTrusted, err := signatures.VerifySignature("notation", []byte(""), "", manifestDigest, manifestContent, repo) + _, _, isTrusted, err := imagetrust.VerifySignature("notation", []byte(""), "", manifestDigest, manifestContent, repo) So(err, ShouldNotBeNil) So(isTrusted, ShouldBeFalse) }) @@ -320,32 +324,32 @@ func TestVerifySignatures(t *testing.T) { Convey("trustpolicy.json does not exist", func() { dir := t.TempDir() - err := signatures.InitNotationDir(dir) + err := imagetrust.InitNotationDir(dir) So(err, ShouldBeNil) - notationDir, _ := signatures.GetNotationDirPath() + notationDir, _ := imagetrust.GetNotationDirPath() err = os.Remove(path.Join(notationDir, "trustpolicy.json")) So(err, ShouldBeNil) - _, _, _, err = signatures.VerifySignature("notation", []byte("signature"), "", manifestDigest, manifestContent, repo) + _, _, _, err = imagetrust.VerifySignature("notation", []byte("signature"), "", manifestDigest, manifestContent, repo) So(err, ShouldNotBeNil) }) Convey("trustpolicy.json has invalid content", func() { dir := t.TempDir() - err := signatures.InitNotationDir(dir) + err := imagetrust.InitNotationDir(dir) So(err, ShouldBeNil) - notationDir, err := signatures.GetNotationDirPath() + notationDir, err := imagetrust.GetNotationDirPath() So(err, ShouldBeNil) err = test.WriteFileWithPermission(path.Join(notationDir, "trustpolicy.json"), []byte("invalid content"), 0o600, true) So(err, ShouldBeNil) - _, _, _, err = signatures.VerifySignature("notation", []byte("signature"), "", manifestDigest, manifestContent, + _, _, _, err = imagetrust.VerifySignature("notation", []byte("signature"), "", manifestDigest, manifestContent, repo) So(err, ShouldNotBeNil) }) @@ -368,10 +372,10 @@ func TestVerifySignatures(t *testing.T) { err := test.UploadImage(image, baseURL, repo, tag) So(err, ShouldBeNil) - err = signatures.InitNotationDir(rootDir) + err = imagetrust.InitNotationDir(rootDir) So(err, ShouldBeNil) - notationDir, err := signatures.GetNotationDirPath() + notationDir, err := imagetrust.GetNotationDirPath() So(err, ShouldBeNil) test.NotationPathLock.Lock() @@ -444,7 +448,7 @@ func TestVerifySignatures(t *testing.T) { } // signature is trusted - author, _, isTrusted, err := signatures.VerifySignature("notation", rawSignature, sigKey, manifestDigest, + author, _, isTrusted, err := imagetrust.VerifySignature("notation", rawSignature, sigKey, manifestDigest, manifestContent, repo) So(err, ShouldBeNil) So(isTrusted, ShouldBeTrue) @@ -454,7 +458,7 @@ func TestVerifySignatures(t *testing.T) { So(err, ShouldBeNil) // signature is not trusted - author, _, isTrusted, err = signatures.VerifySignature("notation", rawSignature, sigKey, manifestDigest, + author, _, isTrusted, err = imagetrust.VerifySignature("notation", rawSignature, sigKey, manifestDigest, manifestContent, repo) So(err, ShouldNotBeNil) So(isTrusted, ShouldBeFalse) @@ -465,23 +469,23 @@ func TestVerifySignatures(t *testing.T) { func TestCheckExpiryErr(t *testing.T) { Convey("no expiry err", t, func() { - isExpiryErr := signatures.CheckExpiryErr([]*notation.ValidationResult{{Error: nil, Type: "wrongtype"}}, time.Now(), + isExpiryErr := imagetrust.CheckExpiryErr([]*notation.ValidationResult{{Error: nil, Type: "wrongtype"}}, time.Now(), nil) So(isExpiryErr, ShouldBeFalse) - isExpiryErr = signatures.CheckExpiryErr([]*notation.ValidationResult{{ + isExpiryErr = imagetrust.CheckExpiryErr([]*notation.ValidationResult{{ Error: nil, Type: trustpolicy.TypeAuthenticTimestamp, }}, time.Now(), errExpiryError) So(isExpiryErr, ShouldBeFalse) }) Convey("expiry err", t, func() { - isExpiryErr := signatures.CheckExpiryErr([]*notation.ValidationResult{ + isExpiryErr := imagetrust.CheckExpiryErr([]*notation.ValidationResult{ {Error: errExpiryError, Type: trustpolicy.TypeExpiry}, }, time.Now(), errExpiryError) So(isExpiryErr, ShouldBeTrue) - isExpiryErr = signatures.CheckExpiryErr([]*notation.ValidationResult{ + isExpiryErr = imagetrust.CheckExpiryErr([]*notation.ValidationResult{ {Error: errExpiryError, Type: trustpolicy.TypeAuthenticTimestamp}, }, time.Now().AddDate(0, 0, -1), errExpiryError) So(isExpiryErr, ShouldBeTrue) @@ -490,7 +494,7 @@ func TestCheckExpiryErr(t *testing.T) { func TestUploadPublicKey(t *testing.T) { Convey("public key - invalid content", t, func() { - err := signatures.UploadPublicKey([]byte("wrong content")) + err := imagetrust.UploadPublicKey([]byte("wrong content")) So(err, ShouldNotBeNil) }) @@ -513,41 +517,41 @@ func TestUploadPublicKey(t *testing.T) { So(err, ShouldBeNil) So(publicKeyContent, ShouldNotBeNil) - err = signatures.InitCosignDir(rootDir) + err = imagetrust.InitCosignDir(rootDir) So(err, ShouldBeNil) - err = signatures.UploadPublicKey(publicKeyContent) + err = imagetrust.UploadPublicKey(publicKeyContent) So(err, ShouldBeNil) }) } func TestUploadCertificate(t *testing.T) { Convey("invalid truststore type", t, func() { - err := signatures.UploadCertificate([]byte("certificate content"), "wrongType", "store") + err := imagetrust.UploadCertificate([]byte("certificate content"), "wrongType", "store") So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrInvalidTruststoreType) }) Convey("invalid truststore name", t, func() { - err := signatures.UploadCertificate([]byte("certificate content"), "ca", "*store?") + err := imagetrust.UploadCertificate([]byte("certificate content"), "ca", "*store?") So(err, ShouldNotBeNil) So(err, ShouldEqual, zerr.ErrInvalidTruststoreName) }) Convey("invalid certificate content", t, func() { - err := signatures.UploadCertificate([]byte("invalid content"), "ca", "store") + err := imagetrust.UploadCertificate([]byte("invalid content"), "ca", "store") So(err, ShouldNotBeNil) content := `-----BEGIN CERTIFICATE----- -----END CERTIFICATE----- ` - err = signatures.UploadCertificate([]byte(content), "ca", "store") + err = imagetrust.UploadCertificate([]byte(content), "ca", "store") So(err, ShouldNotBeNil) content = `` - err = signatures.UploadCertificate([]byte(content), "ca", "store") + err = imagetrust.UploadCertificate([]byte(content), "ca", "store") So(err, ShouldNotBeNil) }) @@ -567,16 +571,16 @@ func TestUploadCertificate(t *testing.T) { So(err, ShouldBeNil) So(certificateContent, ShouldNotBeNil) - err = signatures.InitNotationDir(rootDir) + err = imagetrust.InitNotationDir(rootDir) So(err, ShouldBeNil) - notationDir, err := signatures.GetNotationDirPath() + notationDir, err := imagetrust.GetNotationDirPath() So(err, ShouldBeNil) err = os.Chmod(notationDir, 0o100) So(err, ShouldBeNil) - err = signatures.UploadCertificate(certificateContent, "ca", "notation-upload-test") + err = imagetrust.UploadCertificate(certificateContent, "ca", "notation-upload-test") So(err, ShouldNotBeNil) err = os.Chmod(notationDir, 0o777) @@ -599,10 +603,10 @@ func TestUploadCertificate(t *testing.T) { So(err, ShouldBeNil) So(certificateContent, ShouldNotBeNil) - err = signatures.InitNotationDir(rootDir) + err = imagetrust.InitNotationDir(rootDir) So(err, ShouldBeNil) - notationDir, err := signatures.GetNotationDirPath() + notationDir, err := imagetrust.GetNotationDirPath() So(err, ShouldBeNil) err = os.MkdirAll(path.Join(notationDir, "truststore/x509/ca/notation-upload-test"), 0o777) @@ -611,7 +615,7 @@ func TestUploadCertificate(t *testing.T) { err = os.Chmod(path.Join(notationDir, "truststore/x509/ca/notation-upload-test"), 0o100) So(err, ShouldBeNil) - err = signatures.UploadCertificate(certificateContent, "ca", "notation-upload-test") + err = imagetrust.UploadCertificate(certificateContent, "ca", "notation-upload-test") So(err, ShouldNotBeNil) }) @@ -631,17 +635,17 @@ func TestUploadCertificate(t *testing.T) { So(err, ShouldBeNil) So(certificateContent, ShouldNotBeNil) - err = signatures.InitNotationDir(rootDir) + err = imagetrust.InitNotationDir(rootDir) So(err, ShouldBeNil) - notationDir, err := signatures.GetNotationDirPath() + notationDir, err := imagetrust.GetNotationDirPath() So(err, ShouldBeNil) err = test.WriteFileWithPermission(path.Join(notationDir, "trustpolicy.json"), []byte("invalid content"), 0o600, true) So(err, ShouldBeNil) - err = signatures.UploadCertificate(certificateContent, "ca", "notation-upload-test") + err = imagetrust.UploadCertificate(certificateContent, "ca", "notation-upload-test") So(err, ShouldNotBeNil) }) @@ -661,13 +665,13 @@ func TestUploadCertificate(t *testing.T) { So(err, ShouldBeNil) So(certificateContent, ShouldNotBeNil) - err = signatures.InitNotationDir(rootDir) + err = imagetrust.InitNotationDir(rootDir) So(err, ShouldBeNil) - notationDir, err := signatures.GetNotationDirPath() + notationDir, err := imagetrust.GetNotationDirPath() So(err, ShouldBeNil) - trustpolicyDoc, err := signatures.LoadTrustPolicyDocument(notationDir) + trustpolicyDoc, err := imagetrust.LoadTrustPolicyDocument(notationDir) So(err, ShouldBeNil) trustpolicyDoc.TrustPolicies[0].TrustStores = append(trustpolicyDoc.TrustPolicies[0].TrustStores, @@ -679,7 +683,7 @@ func TestUploadCertificate(t *testing.T) { err = os.WriteFile(path.Join(notationDir, "trustpolicy.json"), trustpolicyDocContent, 0o400) So(err, ShouldBeNil) - err = signatures.UploadCertificate(certificateContent, "ca", "notation-upload-test") + err = imagetrust.UploadCertificate(certificateContent, "ca", "notation-upload-test") So(err, ShouldBeNil) }) @@ -699,10 +703,10 @@ func TestUploadCertificate(t *testing.T) { So(err, ShouldBeNil) So(certificateContent, ShouldNotBeNil) - err = signatures.InitNotationDir(rootDir) + err = imagetrust.InitNotationDir(rootDir) So(err, ShouldBeNil) - err = signatures.UploadCertificate(certificateContent, "ca", "notation-upload-test") + err = imagetrust.UploadCertificate(certificateContent, "ca", "notation-upload-test") So(err, ShouldBeNil) }) } diff --git a/pkg/meta/signatures/notation.go b/pkg/extensions/imagetrust/notation.go similarity index 99% rename from pkg/meta/signatures/notation.go rename to pkg/extensions/imagetrust/notation.go index 6f195cdf..113fb18c 100644 --- a/pkg/meta/signatures/notation.go +++ b/pkg/extensions/imagetrust/notation.go @@ -1,4 +1,7 @@ -package signatures +//go:build imagetrust +// +build imagetrust + +package imagetrust import ( "context" diff --git a/pkg/extensions/sync/sync_test.go b/pkg/extensions/sync/sync_test.go index 3e0f7f8f..1a7c0191 100644 --- a/pkg/extensions/sync/sync_test.go +++ b/pkg/extensions/sync/sync_test.go @@ -39,11 +39,11 @@ import ( "zotregistry.io/zot/pkg/api/config" "zotregistry.io/zot/pkg/api/constants" "zotregistry.io/zot/pkg/cli" + zcommon "zotregistry.io/zot/pkg/common" extconf "zotregistry.io/zot/pkg/extensions/config" syncconf "zotregistry.io/zot/pkg/extensions/config/sync" "zotregistry.io/zot/pkg/extensions/sync" "zotregistry.io/zot/pkg/log" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" storageConstants "zotregistry.io/zot/pkg/storage/constants" "zotregistry.io/zot/pkg/test" @@ -872,7 +872,7 @@ func TestOnDemand(t *testing.T) { AddManifestSignatureFn: func(repo string, signedManifestDigest godigest.Digest, sm mTypes.SignatureMetadata, ) error { - if sm.SignatureType == signatures.CosignSignature || sm.SignatureType == signatures.NotationSignature { + if sm.SignatureType == zcommon.CosignSignature || sm.SignatureType == zcommon.NotationSignature { return sync.ErrTestError } @@ -4511,10 +4511,10 @@ func TestSyncedSignaturesMetaDB(t *testing.T) { So(repoMeta.Signatures, ShouldContainKey, signedImage.DigestStr()) imageSignatures := repoMeta.Signatures[signedImage.DigestStr()] - So(imageSignatures, ShouldContainKey, signatures.CosignSignature) - So(len(imageSignatures[signatures.CosignSignature]), ShouldEqual, 1) - So(imageSignatures, ShouldContainKey, signatures.NotationSignature) - So(len(imageSignatures[signatures.NotationSignature]), ShouldEqual, 1) + So(imageSignatures, ShouldContainKey, zcommon.CosignSignature) + So(len(imageSignatures[zcommon.CosignSignature]), ShouldEqual, 1) + So(imageSignatures, ShouldContainKey, zcommon.NotationSignature) + So(len(imageSignatures[zcommon.NotationSignature]), ShouldEqual, 1) }) } diff --git a/pkg/meta/boltdb/boltdb.go b/pkg/meta/boltdb/boltdb.go index a0a6aaaf..2b1c00a2 100644 --- a/pkg/meta/boltdb/boltdb.go +++ b/pkg/meta/boltdb/boltdb.go @@ -14,9 +14,9 @@ import ( zerr "zotregistry.io/zot/errors" zcommon "zotregistry.io/zot/pkg/common" + "zotregistry.io/zot/pkg/extensions/imagetrust" "zotregistry.io/zot/pkg/log" "zotregistry.io/zot/pkg/meta/common" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" "zotregistry.io/zot/pkg/meta/version" localCtx "zotregistry.io/zot/pkg/requestcontext" @@ -778,7 +778,7 @@ func (bdw *BoltDB) UpdateSignaturesValidity(repo string, manifestDigest godigest layersInfo := []mTypes.LayerInfo{} for _, layerInfo := range sigInfo.LayersInfo { - author, date, isTrusted, _ := signatures.VerifySignature(sigType, layerInfo.LayerContent, layerInfo.SignatureKey, + author, date, isTrusted, _ := imagetrust.VerifySignature(sigType, layerInfo.LayerContent, layerInfo.SignatureKey, manifestDigest, blob, repo) if isTrusted { @@ -869,12 +869,12 @@ func (bdw *BoltDB) AddManifestSignature(repo string, signedManifestDigest godige signatureSlice := manifestSignatures[sygMeta.SignatureType] if !common.SignatureAlreadyExists(signatureSlice, sygMeta) { - if sygMeta.SignatureType == signatures.NotationSignature { + if sygMeta.SignatureType == zcommon.NotationSignature { signatureSlice = append(signatureSlice, mTypes.SignatureInfo{ SignatureManifestDigest: sygMeta.SignatureDigest, LayersInfo: sygMeta.LayersInfo, }) - } else if sygMeta.SignatureType == signatures.CosignSignature { + } else if sygMeta.SignatureType == zcommon.CosignSignature { signatureSlice = []mTypes.SignatureInfo{{ SignatureManifestDigest: sygMeta.SignatureDigest, LayersInfo: sygMeta.LayersInfo, diff --git a/pkg/meta/boltdb/boltdb_test.go b/pkg/meta/boltdb/boltdb_test.go index c529a30a..1882322f 100644 --- a/pkg/meta/boltdb/boltdb_test.go +++ b/pkg/meta/boltdb/boltdb_test.go @@ -14,9 +14,9 @@ import ( "go.etcd.io/bbolt" zerr "zotregistry.io/zot/errors" + zcommon "zotregistry.io/zot/pkg/common" "zotregistry.io/zot/pkg/log" "zotregistry.io/zot/pkg/meta/boltdb" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" localCtx "zotregistry.io/zot/pkg/requestcontext" "zotregistry.io/zot/pkg/test" @@ -545,9 +545,9 @@ func TestWrapperErrors(t *testing.T) { repoData, err := boltdbWrapper.GetRepoMeta("repo1") So(err, ShouldBeNil) - So(len(repoData.Signatures[string(digest.FromString("dig"))][signatures.CosignSignature]), + So(len(repoData.Signatures[string(digest.FromString("dig"))][zcommon.CosignSignature]), ShouldEqual, 1) - So(repoData.Signatures[string(digest.FromString("dig"))][signatures.CosignSignature][0].SignatureManifestDigest, + So(repoData.Signatures[string(digest.FromString("dig"))][zcommon.CosignSignature][0].SignatureManifestDigest, ShouldEqual, "digest2") err = boltdbWrapper.AddManifestSignature("repo1", digest.FromString("dig"), diff --git a/pkg/meta/dynamodb/dynamodb.go b/pkg/meta/dynamodb/dynamodb.go index d889cddc..c5c70938 100644 --- a/pkg/meta/dynamodb/dynamodb.go +++ b/pkg/meta/dynamodb/dynamodb.go @@ -17,9 +17,9 @@ import ( zerr "zotregistry.io/zot/errors" zcommon "zotregistry.io/zot/pkg/common" + "zotregistry.io/zot/pkg/extensions/imagetrust" "zotregistry.io/zot/pkg/log" "zotregistry.io/zot/pkg/meta/common" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" "zotregistry.io/zot/pkg/meta/version" localCtx "zotregistry.io/zot/pkg/requestcontext" @@ -658,7 +658,7 @@ func (dwr *DynamoDB) UpdateSignaturesValidity(repo string, manifestDigest godige layersInfo := []mTypes.LayerInfo{} for _, layerInfo := range sigInfo.LayersInfo { - author, date, isTrusted, _ := signatures.VerifySignature(sigType, layerInfo.LayerContent, layerInfo.SignatureKey, + author, date, isTrusted, _ := imagetrust.VerifySignature(sigType, layerInfo.LayerContent, layerInfo.SignatureKey, manifestDigest, blob, repo) if isTrusted { @@ -727,12 +727,12 @@ func (dwr *DynamoDB) AddManifestSignature(repo string, signedManifestDigest godi signatureSlice := manifestSignatures[sygMeta.SignatureType] if !common.SignatureAlreadyExists(signatureSlice, sygMeta) { - if sygMeta.SignatureType == signatures.NotationSignature { + if sygMeta.SignatureType == zcommon.NotationSignature { signatureSlice = append(signatureSlice, mTypes.SignatureInfo{ SignatureManifestDigest: sygMeta.SignatureDigest, LayersInfo: sygMeta.LayersInfo, }) - } else if sygMeta.SignatureType == signatures.CosignSignature { + } else if sygMeta.SignatureType == zcommon.CosignSignature { signatureSlice = []mTypes.SignatureInfo{{ SignatureManifestDigest: sygMeta.SignatureDigest, LayersInfo: sygMeta.LayersInfo, diff --git a/pkg/meta/meta.go b/pkg/meta/meta.go index 2ded9f4d..30ca29ec 100644 --- a/pkg/meta/meta.go +++ b/pkg/meta/meta.go @@ -6,10 +6,10 @@ import ( "zotregistry.io/zot/errors" "zotregistry.io/zot/pkg/api/config" + "zotregistry.io/zot/pkg/extensions/imagetrust" "zotregistry.io/zot/pkg/log" "zotregistry.io/zot/pkg/meta/boltdb" mdynamodb "zotregistry.io/zot/pkg/meta/dynamodb" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" ) @@ -33,7 +33,7 @@ func New(storageConfig config.StorageConfig, log log.Logger) (mTypes.MetaDB, err return nil, err } - err = signatures.InitCosignAndNotationDirs(params.RootDir) + err = imagetrust.InitCosignAndNotationDirs(params.RootDir) if err != nil { return nil, err } diff --git a/pkg/meta/meta_test.go b/pkg/meta/meta_test.go index e63fced3..01120619 100644 --- a/pkg/meta/meta_test.go +++ b/pkg/meta/meta_test.go @@ -1,3 +1,6 @@ +//go:build imagetrust +// +build imagetrust + package meta_test import ( @@ -20,12 +23,12 @@ import ( . "github.com/smartystreets/goconvey/convey" "zotregistry.io/zot/pkg/api/config" + "zotregistry.io/zot/pkg/extensions/imagetrust" "zotregistry.io/zot/pkg/log" "zotregistry.io/zot/pkg/meta" "zotregistry.io/zot/pkg/meta/boltdb" "zotregistry.io/zot/pkg/meta/common" mdynamodb "zotregistry.io/zot/pkg/meta/dynamodb" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" localCtx "zotregistry.io/zot/pkg/requestcontext" "zotregistry.io/zot/pkg/test" @@ -1208,7 +1211,7 @@ func RunMetaDBTests(t *testing.T, metaDB mTypes.MetaDB, preparationFuncs ...func }) So(err, ShouldBeNil) - err = signatures.InitNotationDir(tdir) + err = imagetrust.InitNotationDir(tdir) So(err, ShouldBeNil) trustpolicyPath := path.Join(tdir, "_notation/trustpolicy.json") diff --git a/pkg/meta/parse.go b/pkg/meta/parse.go index 1ffcc4f7..c2e5f4b4 100644 --- a/pkg/meta/parse.go +++ b/pkg/meta/parse.go @@ -11,7 +11,6 @@ import ( zerr "zotregistry.io/zot/errors" zcommon "zotregistry.io/zot/pkg/common" "zotregistry.io/zot/pkg/log" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" "zotregistry.io/zot/pkg/storage" storageTypes "zotregistry.io/zot/pkg/storage/types" @@ -225,9 +224,9 @@ func GetSignatureLayersInfo(repo, tag, manifestDigest, signatureType string, man imageStore storageTypes.ImageStore, log log.Logger, ) ([]mTypes.LayerInfo, error) { switch signatureType { - case signatures.CosignSignature: + case zcommon.CosignSignature: return getCosignSignatureLayersInfo(repo, tag, manifestDigest, manifestBlob, imageStore, log) - case signatures.NotationSignature: + case zcommon.NotationSignature: return getNotationSignatureLayersInfo(repo, manifestDigest, manifestBlob, imageStore, log) default: return []mTypes.LayerInfo{}, nil @@ -256,7 +255,7 @@ func getCosignSignatureLayersInfo( return layers, err } - layerSigKey, ok := layer.Annotations[signatures.CosignSigKey] + layerSigKey, ok := layer.Annotations[zcommon.CosignSigKey] if !ok { log.Error().Err(err).Str("repository", repo).Str("reference", tag).Str("layerDigest", layer.Digest.String()).Msg( "load-repo: unable to get specific annotation of cosign signature") diff --git a/pkg/meta/parse_test.go b/pkg/meta/parse_test.go index 5334f332..13f016fb 100644 --- a/pkg/meta/parse_test.go +++ b/pkg/meta/parse_test.go @@ -14,12 +14,12 @@ import ( . "github.com/smartystreets/goconvey/convey" zerr "zotregistry.io/zot/errors" + zcommon "zotregistry.io/zot/pkg/common" "zotregistry.io/zot/pkg/extensions/monitoring" "zotregistry.io/zot/pkg/log" "zotregistry.io/zot/pkg/meta" "zotregistry.io/zot/pkg/meta/boltdb" "zotregistry.io/zot/pkg/meta/dynamodb" - "zotregistry.io/zot/pkg/meta/signatures" mTypes "zotregistry.io/zot/pkg/meta/types" "zotregistry.io/zot/pkg/storage" "zotregistry.io/zot/pkg/storage/local" @@ -611,11 +611,11 @@ func TestGetSignatureLayersInfo(t *testing.T) { }) Convey("error while unmarshaling manifest content", t, func() { - _, err := meta.GetSignatureLayersInfo("repo", "tag", "123", signatures.CosignSignature, []byte("bad manifest"), + _, err := meta.GetSignatureLayersInfo("repo", "tag", "123", zcommon.CosignSignature, []byte("bad manifest"), nil, log.NewLogger("debug", "")) So(err, ShouldNotBeNil) - _, err = meta.GetSignatureLayersInfo("repo", "tag", "123", signatures.NotationSignature, []byte("bad manifest"), + _, err = meta.GetSignatureLayersInfo("repo", "tag", "123", zcommon.NotationSignature, []byte("bad manifest"), nil, log.NewLogger("debug", "")) So(err, ShouldNotBeNil) }) diff --git a/pkg/storage/common/common.go b/pkg/storage/common/common.go index 4e020e64..ad5643ef 100644 --- a/pkg/storage/common/common.go +++ b/pkg/storage/common/common.go @@ -17,7 +17,6 @@ import ( ispec "github.com/opencontainers/image-spec/specs-go/v1" oras "github.com/oras-project/artifacts-spec/specs-go/v1" "github.com/rs/zerolog" - "github.com/sigstore/cosign/v2/pkg/oci/remote" zerr "zotregistry.io/zot/errors" zcommon "zotregistry.io/zot/pkg/common" @@ -26,7 +25,11 @@ import ( storageTypes "zotregistry.io/zot/pkg/storage/types" ) -const manifestWithEmptyLayersErrMsg = "layers: Array must have at least 1 items" +const ( + manifestWithEmptyLayersErrMsg = "layers: Array must have at least 1 items" + + cosignSignatureTagSuffix = "sig" +) func GetTagsByIndex(index ispec.Index) []string { tags := make([]string, 0) @@ -559,7 +562,7 @@ func IsSignature(descriptor ispec.Descriptor) bool { switch descriptor.MediaType { case ispec.MediaTypeImageManifest: // is cosgin signature - if strings.HasPrefix(tag, "sha256-") && strings.HasSuffix(tag, remote.SignatureTagSuffix) { + if strings.HasPrefix(tag, "sha256-") && strings.HasSuffix(tag, cosignSignatureTagSuffix) { return true } diff --git a/pkg/storage/local/local.go b/pkg/storage/local/local.go index 32698cd5..6f8abde6 100644 --- a/pkg/storage/local/local.go +++ b/pkg/storage/local/local.go @@ -26,7 +26,6 @@ import ( "github.com/opencontainers/umoci/oci/casext" oras "github.com/oras-project/artifacts-spec/specs-go/v1" "github.com/rs/zerolog" - "github.com/sigstore/cosign/v2/pkg/oci/remote" zerr "zotregistry.io/zot/errors" zcommon "zotregistry.io/zot/pkg/common" @@ -41,6 +40,11 @@ import ( "zotregistry.io/zot/pkg/test/inject" ) +const ( + cosignSignatureTagSuffix = "sig" + SBOMTagSuffix = "sbom" +) + // ImageStoreLocal provides the image storage operations. type ImageStoreLocal struct { rootDir string @@ -1547,8 +1551,8 @@ func (is *ImageStoreLocal) garbageCollect(dir string, repo string) error { tag, ok := desc.Annotations[ispec.AnnotationRefName] if ok { // gather cosign references - if strings.HasPrefix(tag, "sha256-") && (strings.HasSuffix(tag, remote.SignatureTagSuffix) || - strings.HasSuffix(tag, remote.SBOMTagSuffix)) { + if strings.HasPrefix(tag, "sha256-") && (strings.HasSuffix(tag, cosignSignatureTagSuffix) || + strings.HasSuffix(tag, SBOMTagSuffix)) { cosignDescriptors = append(cosignDescriptors, desc) continue @@ -1680,13 +1684,13 @@ func gcCosignReferences(imgStore *ImageStoreLocal, oci casext.Engine, index *isp // check if we can find the manifest which the reference points to for _, desc := range index.Manifests { // signature - subject := fmt.Sprintf("sha256-%s.%s", desc.Digest.Encoded(), remote.SignatureTagSuffix) + subject := fmt.Sprintf("sha256-%s.%s", desc.Digest.Encoded(), cosignSignatureTagSuffix) if subject == cosignDesc.Annotations[ispec.AnnotationRefName] { foundSubject = true } // sbom - subject = fmt.Sprintf("sha256-%s.%s", desc.Digest.Encoded(), remote.SBOMTagSuffix) + subject = fmt.Sprintf("sha256-%s.%s", desc.Digest.Encoded(), SBOMTagSuffix) if subject == cosignDesc.Annotations[ispec.AnnotationRefName] { foundSubject = true }