diff --git a/attestation/types.go b/attestation/types.go index 2da43db..043312d 100644 --- a/attestation/types.go +++ b/attestation/types.go @@ -69,13 +69,13 @@ type Extension struct { type EnvelopeReference struct { *Envelope - ResourceDescriptor *ResourceDescriptor + ResourceDescriptor *ResourceDescriptor `json:"resourceDescriptor"` } type ResourceDescriptor struct { MediaType string `json:"mediaType"` Digest map[string]string `json:"digest"` - URI string `json:"uri"` + URI string `json:"uri,omitempty"` } type AnnotatedStatement struct { diff --git a/attestation/vsa.go b/attestation/vsa.go index e580601..8ebd398 100644 --- a/attestation/vsa.go +++ b/attestation/vsa.go @@ -12,13 +12,13 @@ const ( ) type VSAPredicate struct { - Verifier VSAVerifier `json:"verifier"` - TimeVerified string `json:"timeVerified"` - ResourceURI string `json:"resourceUri"` - Policy VSAPolicy `json:"policy"` - InputAttestations []VSAInputAttestation `json:"inputAttestations,omitempty"` - VerificationResult string `json:"verificationResult"` - VerifiedLevels []string `json:"verifiedLevels"` + Verifier VSAVerifier `json:"verifier"` + TimeVerified string `json:"timeVerified"` + ResourceURI string `json:"resourceUri"` + Policy VSAPolicy `json:"policy"` + InputAttestations []ResourceDescriptor `json:"inputAttestations,omitempty"` + VerificationResult string `json:"verificationResult"` + VerifiedLevels []string `json:"verifiedLevels"` } type VSAVerifier struct { @@ -31,11 +31,6 @@ type VSAPolicy struct { DownloadLocation string `json:"downloadLocation,omitempty"` } -type VSAInputAttestation struct { - Digest map[string]string `json:"digest"` - MediaType string `json:"mediaType"` -} - func ToVSAResourceURI(sub intoto.Subject) (string, error) { // parse purl purl, err := packageurl.FromString(sub.Name) diff --git a/policy/types.go b/policy/types.go index d9d2873..59a0bfb 100644 --- a/policy/types.go +++ b/policy/types.go @@ -8,10 +8,11 @@ import ( ) type Summary struct { - Subjects []intoto.Subject `json:"subjects"` - SLSALevels []string `json:"slsa_levels"` - Verifier string `json:"verifier"` - PolicyURI string `json:"policy_uri"` + Subjects []intoto.Subject `json:"subjects"` + Inputs []attestation.ResourceDescriptor `json:"input_attestations"` + SLSALevels []string `json:"slsa_levels"` + Verifier string `json:"verifier"` + PolicyURI string `json:"policy_uri"` } type Violation struct { diff --git a/test/testdata/local-policy-pass/policy.rego b/test/testdata/local-policy-pass/policy.rego index 71a3b82..a013cf9 100644 --- a/test/testdata/local-policy-pass/policy.rego +++ b/test/testdata/local-policy-pass/policy.rego @@ -37,11 +37,17 @@ subjects contains subject if { some subject in statement.subject } +inputs contains desc if { + some att in atts + desc := att.resourceDescriptor +} + result := { "success": true, "violations": set(), "summary": { "subjects": subjects, + "input_attestations": inputs, "slsa_levels": ["SLSA_BUILD_LEVEL_3"], "verifier": "docker-official-images", "policy_uri": "https://docker.com/official/policy/v0.1", diff --git a/verify.go b/verify.go index deb0476..04ad31d 100644 --- a/verify.go +++ b/verify.go @@ -189,6 +189,7 @@ func toVerificationResult(p *policy.Policy, input *policy.Input, result *policy. Policy: vsaPolicy, VerificationResult: outcomeStr, VerifiedLevels: result.Summary.SLSALevels, + InputAttestations: result.Summary.Inputs, }, }, }, nil diff --git a/verify_test.go b/verify_test.go index d7e0ff6..dac83ef 100644 --- a/verify_test.go +++ b/verify_test.go @@ -124,7 +124,15 @@ func TestVSA(t *testing.T) { assert.Equal(t, PassPolicyDir+"/policy.rego", attestationPredicate.Policy.DownloadLocation) assert.Equal(t, "https://docker.com/official/policy/v0.1", attestationPredicate.Policy.URI) // this is the digest of the policy file - assert.Equal(t, map[string]string{"sha256": "ae71defe3b9ecebdf4f939a396b68884d0cba3c2c9d78ce5e64146d9487b0ade"}, attestationPredicate.Policy.Digest) + assert.Equal(t, map[string]string{"sha256": "fe1d4973f3521009a3adec206946e12aae935a2aceeb1e01f52b5d4cb9de79a5"}, attestationPredicate.Policy.Digest) + assert.Greater(t, len(attestationPredicate.InputAttestations), 0) + for _, input := range attestationPredicate.InputAttestations { + require.NotEmpty(t, input.Digest) + digest, ok := input.Digest["sha256"] + assert.True(t, ok) + assert.NotEmpty(t, digest) + assert.Contains(t, []string{"application/vnd.in-toto.provenance+dsse", "application/vnd.in-toto.spdx+dsse"}, input.MediaType) + } } func TestVerificationFailure(t *testing.T) {