mirror of
https://github.com/anchore/syft.git
synced 2026-10-30 14:02:26 +01:00
separate CPE definitions from capabilities
Signed-off-by: Alex Goodman <alex.goodman@anchore.com>
This commit is contained in:
@@ -2,6 +2,7 @@ package cyclonedxhelpers
|
||||
|
||||
import (
|
||||
"github.com/CycloneDX/cyclonedx-go"
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
|
||||
"github.com/anchore/syft/internal/log"
|
||||
"github.com/anchore/syft/syft/pkg"
|
||||
@@ -11,7 +12,7 @@ func encodeSingleCPE(p pkg.Package) string {
|
||||
// Since the CPEs in a package are sorted by specificity
|
||||
// we can extract the first CPE as the one to output in cyclonedx
|
||||
if len(p.CPEs) > 0 {
|
||||
return pkg.CPEString(p.CPEs[0])
|
||||
return cpe.String(p.CPEs[0])
|
||||
}
|
||||
return ""
|
||||
}
|
||||
@@ -24,15 +25,15 @@ func encodeCPEs(p pkg.Package) (out []cyclonedx.Property) {
|
||||
}
|
||||
out = append(out, cyclonedx.Property{
|
||||
Name: "syft:cpe23",
|
||||
Value: pkg.CPEString(c),
|
||||
Value: cpe.String(c),
|
||||
})
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
func decodeCPEs(c *cyclonedx.Component) (out []pkg.CPE) {
|
||||
func decodeCPEs(c *cyclonedx.Component) (out []cpe.CPE) {
|
||||
if c.CPE != "" {
|
||||
cp, err := pkg.NewCPE(c.CPE)
|
||||
cp, err := cpe.New(c.CPE)
|
||||
if err != nil {
|
||||
log.Warnf("invalid CPE: %s", c.CPE)
|
||||
} else {
|
||||
@@ -43,7 +44,7 @@ func decodeCPEs(c *cyclonedx.Component) (out []pkg.CPE) {
|
||||
if c.Properties != nil {
|
||||
for _, p := range *c.Properties {
|
||||
if p.Name == "syft:cpe23" {
|
||||
cp, err := pkg.NewCPE(p.Value)
|
||||
cp, err := cpe.New(p.Value)
|
||||
if err != nil {
|
||||
log.Warnf("invalid CPE: %s", p.Value)
|
||||
} else {
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
package cyclonedxhelpers
|
||||
|
||||
import (
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
@@ -9,8 +10,8 @@ import (
|
||||
)
|
||||
|
||||
func Test_encodeCPE(t *testing.T) {
|
||||
testCPE := pkg.MustCPE("cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*")
|
||||
testCPE2 := pkg.MustCPE("cpe:2.3:a:name:name2:3.2:*:*:*:*:*:*:*")
|
||||
testCPE := cpe.Must("cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*")
|
||||
testCPE2 := cpe.Must("cpe:2.3:a:name:name2:3.2:*:*:*:*:*:*:*")
|
||||
tests := []struct {
|
||||
name string
|
||||
input pkg.Package
|
||||
@@ -20,14 +21,14 @@ func Test_encodeCPE(t *testing.T) {
|
||||
// note: since this is an optional field, no value is preferred over NONE or NOASSERTION
|
||||
name: "no metadata",
|
||||
input: pkg.Package{
|
||||
CPEs: []pkg.CPE{},
|
||||
CPEs: []cpe.CPE{},
|
||||
},
|
||||
expected: "",
|
||||
},
|
||||
{
|
||||
name: "single CPE",
|
||||
input: pkg.Package{
|
||||
CPEs: []pkg.CPE{
|
||||
CPEs: []cpe.CPE{
|
||||
testCPE,
|
||||
},
|
||||
},
|
||||
@@ -36,7 +37,7 @@ func Test_encodeCPE(t *testing.T) {
|
||||
{
|
||||
name: "multiple CPEs",
|
||||
input: pkg.Package{
|
||||
CPEs: []pkg.CPE{
|
||||
CPEs: []cpe.CPE{
|
||||
testCPE2,
|
||||
testCPE,
|
||||
},
|
||||
|
||||
@@ -49,7 +49,7 @@ func toSyftModel(bom *cyclonedx.BOM) (*sbom.SBOM, error) {
|
||||
}
|
||||
s := &sbom.SBOM{
|
||||
Artifacts: sbom.Artifacts{
|
||||
PackageCatalog: pkg.NewCatalog(),
|
||||
PackageCatalog: pkg.NewCollection(),
|
||||
LinuxDistribution: linuxReleaseFromComponents(*bom.Components),
|
||||
},
|
||||
Source: meta,
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
package spdxhelpers
|
||||
|
||||
import (
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
"github.com/anchore/syft/syft/pkg"
|
||||
)
|
||||
|
||||
@@ -10,7 +11,7 @@ func ExternalRefs(p pkg.Package) (externalRefs []ExternalRef) {
|
||||
for _, c := range p.CPEs {
|
||||
externalRefs = append(externalRefs, ExternalRef{
|
||||
ReferenceCategory: SecurityReferenceCategory,
|
||||
ReferenceLocator: pkg.CPEString(c),
|
||||
ReferenceLocator: cpe.String(c),
|
||||
ReferenceType: Cpe23ExternalRefType,
|
||||
})
|
||||
}
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
package spdxhelpers
|
||||
|
||||
import (
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
"testing"
|
||||
|
||||
"github.com/anchore/syft/syft/pkg"
|
||||
@@ -8,7 +9,7 @@ import (
|
||||
)
|
||||
|
||||
func Test_ExternalRefs(t *testing.T) {
|
||||
testCPE := pkg.MustCPE("cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*")
|
||||
testCPE := cpe.Must("cpe:2.3:a:name:name:3.2:*:*:*:*:*:*:*")
|
||||
tests := []struct {
|
||||
name string
|
||||
input pkg.Package
|
||||
@@ -17,7 +18,7 @@ func Test_ExternalRefs(t *testing.T) {
|
||||
{
|
||||
name: "cpe + purl",
|
||||
input: pkg.Package{
|
||||
CPEs: []pkg.CPE{
|
||||
CPEs: []cpe.CPE{
|
||||
testCPE,
|
||||
},
|
||||
PURL: "a-purl",
|
||||
@@ -25,7 +26,7 @@ func Test_ExternalRefs(t *testing.T) {
|
||||
expected: []ExternalRef{
|
||||
{
|
||||
ReferenceCategory: SecurityReferenceCategory,
|
||||
ReferenceLocator: pkg.CPEString(testCPE),
|
||||
ReferenceLocator: cpe.String(testCPE),
|
||||
ReferenceType: Cpe23ExternalRefType,
|
||||
},
|
||||
{
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
package spdxhelpers
|
||||
|
||||
import (
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
||||
@@ -20,7 +21,7 @@ func ToSyftModel(doc *spdx.Document2_2) (*sbom.SBOM, error) {
|
||||
|
||||
s := &sbom.SBOM{
|
||||
Artifacts: sbom.Artifacts{
|
||||
PackageCatalog: pkg.NewCatalog(),
|
||||
PackageCatalog: pkg.NewCollection(),
|
||||
FileMetadata: map[file.Coordinates]file.Metadata{},
|
||||
FileDigests: map[file.Coordinates][]file.Digest{},
|
||||
LinuxDistribution: findLinuxReleaseByPURL(doc),
|
||||
@@ -316,10 +317,10 @@ func findPURLValue(p *spdx.Package2_2) string {
|
||||
return ""
|
||||
}
|
||||
|
||||
func extractCPEs(p *spdx.Package2_2) (cpes []pkg.CPE) {
|
||||
func extractCPEs(p *spdx.Package2_2) (cpes []cpe.CPE) {
|
||||
for _, r := range p.PackageExternalReferences {
|
||||
if r.RefType == string(Cpe23ExternalRefType) {
|
||||
cpe, err := pkg.NewCPE(r.Locator)
|
||||
cpe, err := cpe.New(r.Locator)
|
||||
if err != nil {
|
||||
log.Warnf("unable to extract SPDX CPE=%q: %+v", r.Locator, err)
|
||||
continue
|
||||
|
||||
@@ -2,6 +2,7 @@ package testutils
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
@@ -99,7 +100,7 @@ func AssertEncoderAgainstGoldenSnapshot(t *testing.T, format sbom.Format, sbom s
|
||||
|
||||
func ImageInput(t testing.TB, testImage string, options ...ImageOption) sbom.SBOM {
|
||||
t.Helper()
|
||||
catalog := pkg.NewCatalog()
|
||||
catalog := pkg.NewCollection()
|
||||
var cfg imageCfg
|
||||
var img *image.Image
|
||||
for _, opt := range options {
|
||||
@@ -151,7 +152,7 @@ func carriageRedactor(s []byte) []byte {
|
||||
return []byte(msg)
|
||||
}
|
||||
|
||||
func populateImageCatalog(catalog *pkg.Catalog, img *image.Image) {
|
||||
func populateImageCatalog(catalog *pkg.Collection, img *image.Image) {
|
||||
_, ref1, _ := img.SquashedTree().File("/somefile-1.txt", filetree.FollowBasenameLinks)
|
||||
_, ref2, _ := img.SquashedTree().File("/somefile-2.txt", filetree.FollowBasenameLinks)
|
||||
|
||||
@@ -172,8 +173,8 @@ func populateImageCatalog(catalog *pkg.Catalog, img *image.Image) {
|
||||
Version: "1.0.1",
|
||||
},
|
||||
PURL: "a-purl-1",
|
||||
CPEs: []pkg.CPE{
|
||||
pkg.MustCPE("cpe:2.3:*:some:package:1:*:*:*:*:*:*:*"),
|
||||
CPEs: []cpe.CPE{
|
||||
cpe.Must("cpe:2.3:*:some:package:1:*:*:*:*:*:*:*"),
|
||||
},
|
||||
})
|
||||
catalog.Add(pkg.Package{
|
||||
@@ -190,8 +191,8 @@ func populateImageCatalog(catalog *pkg.Catalog, img *image.Image) {
|
||||
Version: "2.0.1",
|
||||
},
|
||||
PURL: "a-purl-2",
|
||||
CPEs: []pkg.CPE{
|
||||
pkg.MustCPE("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"),
|
||||
CPEs: []cpe.CPE{
|
||||
cpe.Must("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"),
|
||||
},
|
||||
})
|
||||
}
|
||||
@@ -227,8 +228,8 @@ func DirectoryInput(t testing.TB) sbom.SBOM {
|
||||
}
|
||||
}
|
||||
|
||||
func newDirectoryCatalog() *pkg.Catalog {
|
||||
catalog := pkg.NewCatalog()
|
||||
func newDirectoryCatalog() *pkg.Collection {
|
||||
catalog := pkg.NewCollection()
|
||||
|
||||
// populate catalog with test data
|
||||
catalog.Add(pkg.Package{
|
||||
@@ -252,8 +253,8 @@ func newDirectoryCatalog() *pkg.Catalog {
|
||||
},
|
||||
},
|
||||
PURL: "a-purl-2",
|
||||
CPEs: []pkg.CPE{
|
||||
pkg.MustCPE("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"),
|
||||
CPEs: []cpe.CPE{
|
||||
cpe.Must("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"),
|
||||
},
|
||||
})
|
||||
catalog.Add(pkg.Package{
|
||||
@@ -270,8 +271,8 @@ func newDirectoryCatalog() *pkg.Catalog {
|
||||
Version: "2.0.1",
|
||||
},
|
||||
PURL: "a-purl-2",
|
||||
CPEs: []pkg.CPE{
|
||||
pkg.MustCPE("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"),
|
||||
CPEs: []cpe.CPE{
|
||||
cpe.Must("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"),
|
||||
},
|
||||
})
|
||||
|
||||
|
||||
@@ -48,7 +48,7 @@ func toFormatModel(s sbom.SBOM) (*model.Document, error) {
|
||||
}, nil
|
||||
}
|
||||
|
||||
func toPackages(catalog *pkg.Catalog, relationships []artifact.Relationship) []model.Package {
|
||||
func toPackages(catalog *pkg.Collection, relationships []artifact.Relationship) []model.Package {
|
||||
packages := make([]model.Package, 0)
|
||||
|
||||
for _, p := range catalog.Sorted() {
|
||||
|
||||
@@ -89,9 +89,9 @@ func toFormatModel(s sbom.SBOM) (*spdx.Document2_2, error) {
|
||||
}, nil
|
||||
}
|
||||
|
||||
// packages populates all Package Information from the package Catalog (see https://spdx.github.io/spdx-spec/3-package-information/)
|
||||
// packages populates all Package Information from the package Collection (see https://spdx.github.io/spdx-spec/3-package-information/)
|
||||
// nolint: funlen
|
||||
func toFormatPackages(catalog *pkg.Catalog) map[spdx.ElementID]*spdx.Package2_2 {
|
||||
func toFormatPackages(catalog *pkg.Collection) map[spdx.ElementID]*spdx.Package2_2 {
|
||||
results := make(map[spdx.ElementID]*spdx.Package2_2)
|
||||
|
||||
for _, p := range catalog.Sorted() {
|
||||
|
||||
@@ -2,6 +2,7 @@ package syftjson
|
||||
|
||||
import (
|
||||
"flag"
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
"testing"
|
||||
|
||||
"github.com/anchore/syft/syft/file"
|
||||
@@ -37,7 +38,7 @@ func TestImageEncoder(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestEncodeFullJSONDocument(t *testing.T) {
|
||||
catalog := pkg.NewCatalog()
|
||||
catalog := pkg.NewCollection()
|
||||
|
||||
p1 := pkg.Package{
|
||||
Name: "package-1",
|
||||
@@ -60,8 +61,8 @@ func TestEncodeFullJSONDocument(t *testing.T) {
|
||||
Files: []pkg.PythonFileRecord{},
|
||||
},
|
||||
PURL: "a-purl-1",
|
||||
CPEs: []pkg.CPE{
|
||||
pkg.MustCPE("cpe:2.3:*:some:package:1:*:*:*:*:*:*:*"),
|
||||
CPEs: []cpe.CPE{
|
||||
cpe.Must("cpe:2.3:*:some:package:1:*:*:*:*:*:*:*"),
|
||||
},
|
||||
}
|
||||
|
||||
@@ -84,8 +85,8 @@ func TestEncodeFullJSONDocument(t *testing.T) {
|
||||
Files: []pkg.DpkgFileRecord{},
|
||||
},
|
||||
PURL: "a-purl-2",
|
||||
CPEs: []pkg.CPE{
|
||||
pkg.MustCPE("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"),
|
||||
CPEs: []cpe.CPE{
|
||||
cpe.Must("cpe:2.3:*:some:package:2:*:*:*:*:*:*:*"),
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
@@ -2,6 +2,7 @@ package syftjson
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
"sort"
|
||||
"strconv"
|
||||
|
||||
@@ -152,7 +153,7 @@ func toFileMetadataEntry(coordinates file.Coordinates, metadata *file.Metadata)
|
||||
}
|
||||
}
|
||||
|
||||
func toPackageModels(catalog *pkg.Catalog) []model.Package {
|
||||
func toPackageModels(catalog *pkg.Collection) []model.Package {
|
||||
artifacts := make([]model.Package, 0)
|
||||
if catalog == nil {
|
||||
return artifacts
|
||||
@@ -167,7 +168,7 @@ func toPackageModels(catalog *pkg.Catalog) []model.Package {
|
||||
func toPackageModel(p pkg.Package) model.Package {
|
||||
var cpes = make([]string, len(p.CPEs))
|
||||
for i, c := range p.CPEs {
|
||||
cpes[i] = pkg.CPEString(c)
|
||||
cpes[i] = cpe.String(c)
|
||||
}
|
||||
|
||||
var licenses = make([]string, 0)
|
||||
|
||||
@@ -4,6 +4,7 @@ import (
|
||||
"github.com/anchore/syft/internal/formats/syftjson/model"
|
||||
"github.com/anchore/syft/internal/log"
|
||||
"github.com/anchore/syft/syft/artifact"
|
||||
"github.com/anchore/syft/syft/cpe"
|
||||
"github.com/anchore/syft/syft/file"
|
||||
"github.com/anchore/syft/syft/linux"
|
||||
"github.com/anchore/syft/syft/pkg"
|
||||
@@ -47,7 +48,7 @@ func toSyftLinuxRelease(d model.LinuxRelease) *linux.Release {
|
||||
}
|
||||
}
|
||||
|
||||
func toSyftRelationships(doc *model.Document, catalog *pkg.Catalog, relationships []model.Relationship) []artifact.Relationship {
|
||||
func toSyftRelationships(doc *model.Document, catalog *pkg.Collection, relationships []model.Relationship) []artifact.Relationship {
|
||||
idMap := make(map[string]interface{})
|
||||
|
||||
for _, p := range catalog.Sorted() {
|
||||
@@ -129,8 +130,8 @@ func toSyftSourceData(s model.Source) *source.Metadata {
|
||||
return nil
|
||||
}
|
||||
|
||||
func toSyftCatalog(pkgs []model.Package) *pkg.Catalog {
|
||||
catalog := pkg.NewCatalog()
|
||||
func toSyftCatalog(pkgs []model.Package) *pkg.Collection {
|
||||
catalog := pkg.NewCollection()
|
||||
for _, p := range pkgs {
|
||||
catalog.Add(toSyftPackage(p))
|
||||
}
|
||||
@@ -138,9 +139,9 @@ func toSyftCatalog(pkgs []model.Package) *pkg.Catalog {
|
||||
}
|
||||
|
||||
func toSyftPackage(p model.Package) pkg.Package {
|
||||
var cpes []pkg.CPE
|
||||
var cpes []cpe.CPE
|
||||
for _, c := range p.CPEs {
|
||||
value, err := pkg.NewCPE(c)
|
||||
value, err := cpe.New(c)
|
||||
if err != nil {
|
||||
log.Warnf("excluding invalid CPE %q: %v", c, err)
|
||||
continue
|
||||
|
||||
Reference in New Issue
Block a user