mirror of
https://github.com/aquasecurity/trivy.git
synced 2025-12-22 15:16:33 -08:00
feat(lang-pkg): add data sources (#1625)
This commit is contained in:
2
go.mod
2
go.mod
@@ -13,7 +13,7 @@ require (
|
|||||||
github.com/aquasecurity/go-npm-version v0.0.0-20201110091526-0b796d180798
|
github.com/aquasecurity/go-npm-version v0.0.0-20201110091526-0b796d180798
|
||||||
github.com/aquasecurity/go-pep440-version v0.0.0-20210121094942-22b2f8951d46
|
github.com/aquasecurity/go-pep440-version v0.0.0-20210121094942-22b2f8951d46
|
||||||
github.com/aquasecurity/go-version v0.0.0-20210121072130-637058cfe492
|
github.com/aquasecurity/go-version v0.0.0-20210121072130-637058cfe492
|
||||||
github.com/aquasecurity/trivy-db v0.0.0-20220119092408-3e43e9ac6def
|
github.com/aquasecurity/trivy-db v0.0.0-20220125230746-e5eec5a98bf1
|
||||||
github.com/caarlos0/env/v6 v6.0.0
|
github.com/caarlos0/env/v6 v6.0.0
|
||||||
github.com/cenkalti/backoff v2.2.1+incompatible
|
github.com/cenkalti/backoff v2.2.1+incompatible
|
||||||
github.com/cheggaaa/pb/v3 v3.0.3
|
github.com/cheggaaa/pb/v3 v3.0.3
|
||||||
|
|||||||
6
go.sum
6
go.sum
@@ -241,10 +241,8 @@ github.com/aquasecurity/testdocker v0.0.0-20210911155206-e1e85f5a1516 h1:moQmzbp
|
|||||||
github.com/aquasecurity/testdocker v0.0.0-20210911155206-e1e85f5a1516/go.mod h1:gTd97VdQ0rg8Mkiic3rPgNOQdprZ7feTAhiD5mGQjgM=
|
github.com/aquasecurity/testdocker v0.0.0-20210911155206-e1e85f5a1516/go.mod h1:gTd97VdQ0rg8Mkiic3rPgNOQdprZ7feTAhiD5mGQjgM=
|
||||||
github.com/aquasecurity/tfsec v0.63.1 h1:KH63HTcUoab7d3PKtqFO6T8K5AY7bzLw7Kiu+EY9U64=
|
github.com/aquasecurity/tfsec v0.63.1 h1:KH63HTcUoab7d3PKtqFO6T8K5AY7bzLw7Kiu+EY9U64=
|
||||||
github.com/aquasecurity/tfsec v0.63.1/go.mod h1:g5ZWmsfqW1FsCaPb9ux8Pzjcyss/WUB2XuRd5slqvnc=
|
github.com/aquasecurity/tfsec v0.63.1/go.mod h1:g5ZWmsfqW1FsCaPb9ux8Pzjcyss/WUB2XuRd5slqvnc=
|
||||||
github.com/aquasecurity/trivy-db v0.0.0-20220116182821-1a83ba8d44cf h1:STzhFjoXPmE+HQzjydti5w5KNvQpUYwaH4y878jq+II=
|
github.com/aquasecurity/trivy-db v0.0.0-20220125230746-e5eec5a98bf1 h1:mOaPyX+hVglWFk8TbLA7q01GnqVcf6yPusaQaWnDNjE=
|
||||||
github.com/aquasecurity/trivy-db v0.0.0-20220116182821-1a83ba8d44cf/go.mod h1:rnojVJTK+RySsfLW7xMqmQRSjQpm5fEjS+/N4kf3fcc=
|
github.com/aquasecurity/trivy-db v0.0.0-20220125230746-e5eec5a98bf1/go.mod h1:rnojVJTK+RySsfLW7xMqmQRSjQpm5fEjS+/N4kf3fcc=
|
||||||
github.com/aquasecurity/trivy-db v0.0.0-20220119092408-3e43e9ac6def h1:2E1Fj1ouevZG/2ii+XgZitDf3h5fyvNeUKduHbpDZr0=
|
|
||||||
github.com/aquasecurity/trivy-db v0.0.0-20220119092408-3e43e9ac6def/go.mod h1:rnojVJTK+RySsfLW7xMqmQRSjQpm5fEjS+/N4kf3fcc=
|
|
||||||
github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o=
|
github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o=
|
||||||
github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8=
|
github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8=
|
||||||
github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY=
|
github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY=
|
||||||
|
|||||||
2
integration/testdata/fixtures/db/ruby.yaml
vendored
2
integration/testdata/fixtures/db/ruby.yaml
vendored
@@ -1,4 +1,4 @@
|
|||||||
- bucket: GitHub Security Advisory Rubygems
|
- bucket: GitHub Security Advisory RubyGems
|
||||||
pairs:
|
pairs:
|
||||||
- bucket: activesupport
|
- bucket: activesupport
|
||||||
pairs:
|
pairs:
|
||||||
|
|||||||
@@ -94,6 +94,10 @@ func (c *ReportOption) Init(logger *zap.SugaredLogger) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (c *ReportOption) populateVulnTypes() error {
|
func (c *ReportOption) populateVulnTypes() error {
|
||||||
|
if c.vulnType == "" {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
for _, v := range strings.Split(c.vulnType, ",") {
|
for _, v := range strings.Split(c.vulnType, ",") {
|
||||||
if types.NewVulnType(v) == types.VulnTypeUnknown {
|
if types.NewVulnType(v) == types.VulnTypeUnknown {
|
||||||
return xerrors.Errorf("unknown vulnerability type (%s)", v)
|
return xerrors.Errorf("unknown vulnerability type (%s)", v)
|
||||||
@@ -104,6 +108,10 @@ func (c *ReportOption) populateVulnTypes() error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (c *ReportOption) populateSecurityChecks() error {
|
func (c *ReportOption) populateSecurityChecks() error {
|
||||||
|
if c.securityChecks == "" {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
for _, v := range strings.Split(c.securityChecks, ",") {
|
for _, v := range strings.Split(c.securityChecks, ",") {
|
||||||
if types.NewSecurityCheck(v) == types.SecurityCheckUnknown {
|
if types.NewSecurityCheck(v) == types.SecurityCheckUnknown {
|
||||||
return xerrors.Errorf("unknown security check (%s)", v)
|
return xerrors.Errorf("unknown security check (%s)", v)
|
||||||
|
|||||||
@@ -49,6 +49,7 @@ func (s *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
PkgName: pkgName,
|
PkgName: pkgName,
|
||||||
InstalledVersion: pkgVer,
|
InstalledVersion: pkgVer,
|
||||||
FixedVersion: s.createFixedVersions(advisory),
|
FixedVersion: s.createFixedVersions(advisory),
|
||||||
|
DataSource: advisory.DataSource,
|
||||||
}
|
}
|
||||||
vulns = append(vulns, vuln)
|
vulns = append(vulns, vuln)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,20 +5,14 @@ import (
|
|||||||
|
|
||||||
"golang.org/x/xerrors"
|
"golang.org/x/xerrors"
|
||||||
|
|
||||||
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
|
||||||
bundlerSrc "github.com/aquasecurity/trivy-db/pkg/vulnsrc/bundler"
|
bundlerSrc "github.com/aquasecurity/trivy-db/pkg/vulnsrc/bundler"
|
||||||
"github.com/aquasecurity/trivy/pkg/types"
|
"github.com/aquasecurity/trivy/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
// VulnSrc defines the operation on bundler vulnerability
|
|
||||||
type VulnSrc interface {
|
|
||||||
Get(pkgName string) ([]bundlerSrc.Advisory, error)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Advisory implements the bundler VulnSrc
|
// Advisory implements the bundler VulnSrc
|
||||||
type Advisory struct {
|
type Advisory struct {
|
||||||
comparer RubyGemsComparer
|
comparer RubyGemsComparer
|
||||||
vs VulnSrc
|
vs bundlerSrc.VulnSrc
|
||||||
}
|
}
|
||||||
|
|
||||||
// NewAdvisory is the factory method to return bundler.Advisory
|
// NewAdvisory is the factory method to return bundler.Advisory
|
||||||
@@ -38,11 +32,7 @@ func (a *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
|
|
||||||
var vulns []types.DetectedVulnerability
|
var vulns []types.DetectedVulnerability
|
||||||
for _, advisory := range advisories {
|
for _, advisory := range advisories {
|
||||||
adv := dbTypes.Advisory{
|
if !a.comparer.IsVulnerable(pkgVer, advisory) {
|
||||||
UnaffectedVersions: advisory.UnaffectedVersions,
|
|
||||||
PatchedVersions: advisory.PatchedVersions,
|
|
||||||
}
|
|
||||||
if !a.comparer.IsVulnerable(pkgVer, adv) {
|
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -51,6 +41,7 @@ func (a *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
PkgName: strings.TrimSpace(pkgName),
|
PkgName: strings.TrimSpace(pkgName),
|
||||||
InstalledVersion: pkgVer,
|
InstalledVersion: pkgVer,
|
||||||
FixedVersion: strings.Join(advisory.PatchedVersions, ", "),
|
FixedVersion: strings.Join(advisory.PatchedVersions, ", "),
|
||||||
|
DataSource: advisory.DataSource,
|
||||||
}
|
}
|
||||||
vulns = append(vulns, vuln)
|
vulns = append(vulns, vuln)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,12 +3,13 @@ package bundler_test
|
|||||||
import (
|
import (
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
"github.com/aquasecurity/trivy/pkg/detector/library/bundler"
|
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
"github.com/stretchr/testify/require"
|
"github.com/stretchr/testify/require"
|
||||||
|
|
||||||
"github.com/aquasecurity/trivy-db/pkg/db"
|
"github.com/aquasecurity/trivy-db/pkg/db"
|
||||||
|
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
||||||
"github.com/aquasecurity/trivy/pkg/dbtest"
|
"github.com/aquasecurity/trivy/pkg/dbtest"
|
||||||
|
"github.com/aquasecurity/trivy/pkg/detector/library/bundler"
|
||||||
"github.com/aquasecurity/trivy/pkg/types"
|
"github.com/aquasecurity/trivy/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -30,13 +31,20 @@ func TestAdvisory_DetectVulnerabilities(t *testing.T) {
|
|||||||
pkgName: "activesupport",
|
pkgName: "activesupport",
|
||||||
pkgVer: "4.1.1",
|
pkgVer: "4.1.1",
|
||||||
},
|
},
|
||||||
fixtures: []string{"testdata/fixtures/gem.yaml"},
|
fixtures: []string{
|
||||||
|
"testdata/fixtures/gem.yaml",
|
||||||
|
"testdata/fixtures/data-source.yaml",
|
||||||
|
},
|
||||||
want: []types.DetectedVulnerability{
|
want: []types.DetectedVulnerability{
|
||||||
{
|
{
|
||||||
PkgName: "activesupport",
|
PkgName: "activesupport",
|
||||||
InstalledVersion: "4.1.1",
|
InstalledVersion: "4.1.1",
|
||||||
VulnerabilityID: "CVE-2015-3226",
|
VulnerabilityID: "CVE-2015-3226",
|
||||||
FixedVersion: ">= 4.2.2, ~> 4.1.11",
|
FixedVersion: ">= 4.2.2, ~> 4.1.11",
|
||||||
|
DataSource: &dbTypes.DataSource{
|
||||||
|
Name: "Ruby Advisory Database",
|
||||||
|
URL: "https://github.com/rubysec/ruby-advisory-db",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@@ -72,10 +80,9 @@ func TestAdvisory_DetectVulnerabilities(t *testing.T) {
|
|||||||
require.NotNil(t, err)
|
require.NotNil(t, err)
|
||||||
assert.Contains(t, err.Error(), tt.wantErr)
|
assert.Contains(t, err.Error(), tt.wantErr)
|
||||||
return
|
return
|
||||||
} else {
|
|
||||||
assert.NoError(t, err)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
assert.NoError(t, err)
|
||||||
assert.Equal(t, tt.want, got)
|
assert.Equal(t, tt.want, got)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
6
pkg/detector/library/bundler/testdata/fixtures/data-source.yaml
vendored
Normal file
6
pkg/detector/library/bundler/testdata/fixtures/data-source.yaml
vendored
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
- bucket: data-source
|
||||||
|
pairs:
|
||||||
|
- key: ruby-advisory-db
|
||||||
|
value:
|
||||||
|
Name: "Ruby Advisory Database"
|
||||||
|
URL: "https://github.com/rubysec/ruby-advisory-db"
|
||||||
@@ -6,7 +6,6 @@ import (
|
|||||||
|
|
||||||
"golang.org/x/xerrors"
|
"golang.org/x/xerrors"
|
||||||
|
|
||||||
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
|
||||||
composerSrc "github.com/aquasecurity/trivy-db/pkg/vulnsrc/composer"
|
composerSrc "github.com/aquasecurity/trivy-db/pkg/vulnsrc/composer"
|
||||||
"github.com/aquasecurity/trivy/pkg/detector/library/comparer"
|
"github.com/aquasecurity/trivy/pkg/detector/library/comparer"
|
||||||
"github.com/aquasecurity/trivy/pkg/types"
|
"github.com/aquasecurity/trivy/pkg/types"
|
||||||
@@ -36,19 +35,18 @@ func (s *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
|
|
||||||
var vulns []types.DetectedVulnerability
|
var vulns []types.DetectedVulnerability
|
||||||
for _, advisory := range advisories {
|
for _, advisory := range advisories {
|
||||||
var affectedVersions []string
|
|
||||||
var patchedVersions []string
|
var patchedVersions []string
|
||||||
for _, branch := range advisory.Branches {
|
for _, vulnerableRange := range advisory.VulnerableVersions {
|
||||||
for _, version := range branch.Versions {
|
// e.g. ">=5, <5.3.1"
|
||||||
if !strings.HasPrefix(version, "<=") && strings.HasPrefix(version, "<") {
|
for _, v := range strings.Split(vulnerableRange, ", ") {
|
||||||
patchedVersions = append(patchedVersions, strings.Trim(version, "<"))
|
// e.g. "<5.3.1"
|
||||||
|
if !strings.HasPrefix(v, "<=") && strings.HasPrefix(v, "<") {
|
||||||
|
patchedVersions = append(patchedVersions, strings.Trim(v, "<"))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
affectedVersions = append(affectedVersions, strings.Join(branch.Versions, ", "))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
adv := dbTypes.Advisory{VulnerableVersions: affectedVersions}
|
if !s.comparer.IsVulnerable(pkgVer, advisory) {
|
||||||
if !s.comparer.IsVulnerable(pkgVer, adv) {
|
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -57,6 +55,7 @@ func (s *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
PkgName: pkgName,
|
PkgName: pkgName,
|
||||||
InstalledVersion: pkgVer,
|
InstalledVersion: pkgVer,
|
||||||
FixedVersion: strings.Join(patchedVersions, ", "),
|
FixedVersion: strings.Join(patchedVersions, ", "),
|
||||||
|
DataSource: advisory.DataSource,
|
||||||
}
|
}
|
||||||
vulns = append(vulns, vuln)
|
vulns = append(vulns, vuln)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import (
|
|||||||
"github.com/stretchr/testify/require"
|
"github.com/stretchr/testify/require"
|
||||||
|
|
||||||
"github.com/aquasecurity/trivy-db/pkg/db"
|
"github.com/aquasecurity/trivy-db/pkg/db"
|
||||||
|
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
||||||
"github.com/aquasecurity/trivy/pkg/dbtest"
|
"github.com/aquasecurity/trivy/pkg/dbtest"
|
||||||
"github.com/aquasecurity/trivy/pkg/detector/library/composer"
|
"github.com/aquasecurity/trivy/pkg/detector/library/composer"
|
||||||
"github.com/aquasecurity/trivy/pkg/types"
|
"github.com/aquasecurity/trivy/pkg/types"
|
||||||
@@ -30,13 +31,20 @@ func TestAdvisory_DetectVulnerabilities(t *testing.T) {
|
|||||||
pkgName: "aws/aws-sdk-php",
|
pkgName: "aws/aws-sdk-php",
|
||||||
pkgVer: "3.2.0",
|
pkgVer: "3.2.0",
|
||||||
},
|
},
|
||||||
fixtures: []string{"testdata/fixtures/composer.yaml"},
|
fixtures: []string{
|
||||||
|
"testdata/fixtures/composer.yaml",
|
||||||
|
"testdata/fixtures/data-source.yaml",
|
||||||
|
},
|
||||||
want: []types.DetectedVulnerability{
|
want: []types.DetectedVulnerability{
|
||||||
{
|
{
|
||||||
PkgName: "aws/aws-sdk-php",
|
PkgName: "aws/aws-sdk-php",
|
||||||
InstalledVersion: "3.2.0",
|
InstalledVersion: "3.2.0",
|
||||||
VulnerabilityID: "CVE-2015-5723",
|
VulnerabilityID: "CVE-2015-5723",
|
||||||
FixedVersion: "3.2.1",
|
FixedVersion: "3.2.1",
|
||||||
|
DataSource: &dbTypes.DataSource{
|
||||||
|
Name: "PHP Security Advisories Database",
|
||||||
|
URL: "https://github.com/FriendsOfPHP/security-advisories",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -4,25 +4,13 @@
|
|||||||
pairs:
|
pairs:
|
||||||
- key: CVE-2015-5723
|
- key: CVE-2015-5723
|
||||||
value:
|
value:
|
||||||
Branches:
|
VulnerableVersions:
|
||||||
3.x:
|
- ">=3.0.0, <3.2.1"
|
||||||
Versions:
|
|
||||||
- ">=3.0.0"
|
|
||||||
- "<3.2.1"
|
|
||||||
- bucket: "composer://guzzlehttp/guzzle"
|
- bucket: "composer://guzzlehttp/guzzle"
|
||||||
pairs:
|
pairs:
|
||||||
- key: CVE-2016-5385
|
- key: CVE-2016-5385
|
||||||
value:
|
value:
|
||||||
Branches:
|
VulnerableVersions:
|
||||||
4.x:
|
- ">=4.0.0rc2, <4.2.4"
|
||||||
Versions:
|
- ">=5, <5.3.1"
|
||||||
- ">=4.0.0rc2"
|
- ">=6, <6.2.1"
|
||||||
- "<4.2.4"
|
|
||||||
5.3:
|
|
||||||
Versions:
|
|
||||||
- ">=5"
|
|
||||||
- "<5.3.1"
|
|
||||||
master:
|
|
||||||
Versions:
|
|
||||||
- ">=6"
|
|
||||||
- "<6.2.1"
|
|
||||||
6
pkg/detector/library/composer/testdata/fixtures/data-source.yaml
vendored
Normal file
6
pkg/detector/library/composer/testdata/fixtures/data-source.yaml
vendored
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
- bucket: data-source
|
||||||
|
pairs:
|
||||||
|
- key: php-security-advisories
|
||||||
|
value:
|
||||||
|
Name: "PHP Security Advisories Database"
|
||||||
|
URL: "https://github.com/FriendsOfPHP/security-advisories"
|
||||||
@@ -4,4 +4,4 @@
|
|||||||
pairs:
|
pairs:
|
||||||
- key: CVE-2015-5723
|
- key: CVE-2015-5723
|
||||||
value:
|
value:
|
||||||
Branches: invalid
|
VulnerableVersions: invalid
|
||||||
|
|||||||
@@ -87,7 +87,7 @@ func (d *Driver) Type() string {
|
|||||||
|
|
||||||
func newRubyGemsDriver() Driver {
|
func newRubyGemsDriver() Driver {
|
||||||
c := bundler.RubyGemsComparer{}
|
c := bundler.RubyGemsComparer{}
|
||||||
return Aggregate(vulnerability.RubyGems, NewAdvisory(vulnerability.RubyGems, c), bundler.NewAdvisory(), ghsa.NewAdvisory(ecosystem.Rubygems, c))
|
return Aggregate(vulnerability.RubyGems, NewAdvisory(vulnerability.RubyGems, c), bundler.NewAdvisory(), ghsa.NewAdvisory(ecosystem.RubyGems, c))
|
||||||
}
|
}
|
||||||
|
|
||||||
func newComposerDriver() Driver {
|
func newComposerDriver() Driver {
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ import (
|
|||||||
|
|
||||||
ftypes "github.com/aquasecurity/fanal/types"
|
ftypes "github.com/aquasecurity/fanal/types"
|
||||||
"github.com/aquasecurity/trivy-db/pkg/db"
|
"github.com/aquasecurity/trivy-db/pkg/db"
|
||||||
|
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
||||||
"github.com/aquasecurity/trivy/pkg/dbtest"
|
"github.com/aquasecurity/trivy/pkg/dbtest"
|
||||||
"github.com/aquasecurity/trivy/pkg/detector/library"
|
"github.com/aquasecurity/trivy/pkg/detector/library"
|
||||||
"github.com/aquasecurity/trivy/pkg/types"
|
"github.com/aquasecurity/trivy/pkg/types"
|
||||||
@@ -27,9 +28,12 @@ func TestDriver_Detect(t *testing.T) {
|
|||||||
wantErr string
|
wantErr string
|
||||||
}{
|
}{
|
||||||
{
|
{
|
||||||
name: "happy path",
|
name: "happy path",
|
||||||
fixtures: []string{"testdata/fixtures/php.yaml"},
|
fixtures: []string{
|
||||||
libType: ftypes.Composer,
|
"testdata/fixtures/php.yaml",
|
||||||
|
"testdata/fixtures/data-source.yaml",
|
||||||
|
},
|
||||||
|
libType: ftypes.Composer,
|
||||||
args: args{
|
args: args{
|
||||||
pkgName: "symfony/symfony",
|
pkgName: "symfony/symfony",
|
||||||
pkgVer: "4.2.6",
|
pkgVer: "4.2.6",
|
||||||
@@ -40,6 +44,10 @@ func TestDriver_Detect(t *testing.T) {
|
|||||||
PkgName: "symfony/symfony",
|
PkgName: "symfony/symfony",
|
||||||
InstalledVersion: "4.2.6",
|
InstalledVersion: "4.2.6",
|
||||||
FixedVersion: "4.2.7",
|
FixedVersion: "4.2.7",
|
||||||
|
DataSource: &dbTypes.DataSource{
|
||||||
|
Name: "GitLab Advisory Database Community",
|
||||||
|
URL: "https://gitlab.com/gitlab-org/advisories-community",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@@ -61,9 +69,12 @@ func TestDriver_Detect(t *testing.T) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "no patched versions in the advisory",
|
name: "no patched versions in the advisory",
|
||||||
fixtures: []string{"testdata/fixtures/php.yaml"},
|
fixtures: []string{
|
||||||
libType: ftypes.Composer,
|
"testdata/fixtures/php.yaml",
|
||||||
|
"testdata/fixtures/data-source.yaml",
|
||||||
|
},
|
||||||
|
libType: ftypes.Composer,
|
||||||
args: args{
|
args: args{
|
||||||
pkgName: "symfony/symfony",
|
pkgName: "symfony/symfony",
|
||||||
pkgVer: "4.4.6",
|
pkgVer: "4.4.6",
|
||||||
@@ -74,13 +85,20 @@ func TestDriver_Detect(t *testing.T) {
|
|||||||
PkgName: "symfony/symfony",
|
PkgName: "symfony/symfony",
|
||||||
InstalledVersion: "4.4.6",
|
InstalledVersion: "4.4.6",
|
||||||
FixedVersion: "4.4.7",
|
FixedVersion: "4.4.7",
|
||||||
|
DataSource: &dbTypes.DataSource{
|
||||||
|
Name: "PHP Security Advisories Database",
|
||||||
|
URL: "https://github.com/FriendsOfPHP/security-advisories",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "no vulnerable versions in the advisory",
|
name: "no vulnerable versions in the advisory",
|
||||||
fixtures: []string{"testdata/fixtures/ruby.yaml"},
|
fixtures: []string{
|
||||||
libType: ftypes.Bundler,
|
"testdata/fixtures/ruby.yaml",
|
||||||
|
"testdata/fixtures/data-source.yaml",
|
||||||
|
},
|
||||||
|
libType: ftypes.Bundler,
|
||||||
args: args{
|
args: args{
|
||||||
pkgName: "activesupport",
|
pkgName: "activesupport",
|
||||||
pkgVer: "4.1.1",
|
pkgVer: "4.1.1",
|
||||||
@@ -91,6 +109,10 @@ func TestDriver_Detect(t *testing.T) {
|
|||||||
PkgName: "activesupport",
|
PkgName: "activesupport",
|
||||||
InstalledVersion: "4.1.1",
|
InstalledVersion: "4.1.1",
|
||||||
FixedVersion: ">= 4.2.2, ~> 4.1.11",
|
FixedVersion: ">= 4.2.2, ~> 4.1.11",
|
||||||
|
DataSource: &dbTypes.DataSource{
|
||||||
|
Name: "Ruby Advisory Database",
|
||||||
|
URL: "https://github.com/rubysec/ruby-advisory-db",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -5,20 +5,14 @@ import (
|
|||||||
|
|
||||||
"golang.org/x/xerrors"
|
"golang.org/x/xerrors"
|
||||||
|
|
||||||
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
|
||||||
"github.com/aquasecurity/trivy-db/pkg/vulnsrc/ghsa"
|
"github.com/aquasecurity/trivy-db/pkg/vulnsrc/ghsa"
|
||||||
"github.com/aquasecurity/trivy/pkg/detector/library/comparer"
|
"github.com/aquasecurity/trivy/pkg/detector/library/comparer"
|
||||||
"github.com/aquasecurity/trivy/pkg/types"
|
"github.com/aquasecurity/trivy/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
// VulnSrc defines the operations on vulnerability source
|
|
||||||
type VulnSrc interface {
|
|
||||||
Get(pkgName string) ([]ghsa.Advisory, error)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Advisory implements VulnSrc
|
// Advisory implements VulnSrc
|
||||||
type Advisory struct {
|
type Advisory struct {
|
||||||
vs VulnSrc
|
vs ghsa.VulnSrc
|
||||||
comparer comparer.Comparer
|
comparer comparer.Comparer
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -39,8 +33,7 @@ func (s *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
|
|
||||||
var vulns []types.DetectedVulnerability
|
var vulns []types.DetectedVulnerability
|
||||||
for _, advisory := range advisories {
|
for _, advisory := range advisories {
|
||||||
adv := dbTypes.Advisory{VulnerableVersions: advisory.VulnerableVersions}
|
if !s.comparer.IsVulnerable(pkgVer, advisory) {
|
||||||
if !s.comparer.IsVulnerable(pkgVer, adv) {
|
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -49,6 +42,7 @@ func (s *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
PkgName: pkgName,
|
PkgName: pkgName,
|
||||||
InstalledVersion: pkgVer,
|
InstalledVersion: pkgVer,
|
||||||
FixedVersion: strings.Join(advisory.PatchedVersions, ", "),
|
FixedVersion: strings.Join(advisory.PatchedVersions, ", "),
|
||||||
|
DataSource: advisory.DataSource,
|
||||||
}
|
}
|
||||||
vulns = append(vulns, vuln)
|
vulns = append(vulns, vuln)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import (
|
|||||||
"github.com/stretchr/testify/require"
|
"github.com/stretchr/testify/require"
|
||||||
|
|
||||||
"github.com/aquasecurity/trivy-db/pkg/db"
|
"github.com/aquasecurity/trivy-db/pkg/db"
|
||||||
|
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
||||||
ghsaSrc "github.com/aquasecurity/trivy-db/pkg/vulnsrc/ghsa"
|
ghsaSrc "github.com/aquasecurity/trivy-db/pkg/vulnsrc/ghsa"
|
||||||
"github.com/aquasecurity/trivy/pkg/dbtest"
|
"github.com/aquasecurity/trivy/pkg/dbtest"
|
||||||
"github.com/aquasecurity/trivy/pkg/detector/library/comparer"
|
"github.com/aquasecurity/trivy/pkg/detector/library/comparer"
|
||||||
@@ -41,13 +42,20 @@ func TestAdvisory_DetectVulnerabilities(t *testing.T) {
|
|||||||
pkgName: "symfony/symfony",
|
pkgName: "symfony/symfony",
|
||||||
pkgVer: "5.1.5-alpha",
|
pkgVer: "5.1.5-alpha",
|
||||||
},
|
},
|
||||||
fixtures: []string{"testdata/fixtures/ghsa.yaml"},
|
fixtures: []string{
|
||||||
|
"testdata/fixtures/ghsa.yaml",
|
||||||
|
"testdata/fixtures/data-source.yaml",
|
||||||
|
},
|
||||||
want: []types.DetectedVulnerability{
|
want: []types.DetectedVulnerability{
|
||||||
{
|
{
|
||||||
PkgName: "symfony/symfony",
|
PkgName: "symfony/symfony",
|
||||||
InstalledVersion: "5.1.5-alpha",
|
InstalledVersion: "5.1.5-alpha",
|
||||||
VulnerabilityID: "CVE-2020-15094",
|
VulnerabilityID: "CVE-2020-15094",
|
||||||
FixedVersion: "5.1.5, 4.4.13",
|
FixedVersion: "5.1.5, 4.4.13",
|
||||||
|
DataSource: &dbTypes.DataSource{
|
||||||
|
Name: "GitHub Security Advisory Composer",
|
||||||
|
URL: "https://github.com/advisories?query=type%%3Areviewed+ecosystem%%3Acomposer",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@@ -61,13 +69,20 @@ func TestAdvisory_DetectVulnerabilities(t *testing.T) {
|
|||||||
pkgName: "AWSSDK.Core",
|
pkgName: "AWSSDK.Core",
|
||||||
pkgVer: "3.5.1.30",
|
pkgVer: "3.5.1.30",
|
||||||
},
|
},
|
||||||
fixtures: []string{"testdata/fixtures/ghsa.yaml"},
|
fixtures: []string{
|
||||||
|
"testdata/fixtures/ghsa.yaml",
|
||||||
|
"testdata/fixtures/data-source.yaml",
|
||||||
|
},
|
||||||
want: []types.DetectedVulnerability{
|
want: []types.DetectedVulnerability{
|
||||||
{
|
{
|
||||||
PkgName: "AWSSDK.Core",
|
PkgName: "AWSSDK.Core",
|
||||||
InstalledVersion: "3.5.1.30",
|
InstalledVersion: "3.5.1.30",
|
||||||
VulnerabilityID: "CVE-2020-99999",
|
VulnerabilityID: "CVE-2020-99999",
|
||||||
FixedVersion: "3.5.1.31",
|
FixedVersion: "3.5.1.31",
|
||||||
|
DataSource: &dbTypes.DataSource{
|
||||||
|
Name: "GitHub Security Advisory Nuget",
|
||||||
|
URL: "https://github.com/advisories?query=type%%3Areviewed+ecosystem%%3Anuget",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|||||||
10
pkg/detector/library/ghsa/testdata/fixtures/data-source.yaml
vendored
Normal file
10
pkg/detector/library/ghsa/testdata/fixtures/data-source.yaml
vendored
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
- bucket: data-source
|
||||||
|
pairs:
|
||||||
|
- key: GitHub Security Advisory Composer
|
||||||
|
value:
|
||||||
|
Name: "GitHub Security Advisory Composer"
|
||||||
|
URL: "https://github.com/advisories?query=type%%3Areviewed+ecosystem%%3Acomposer"
|
||||||
|
- key: GitHub Security Advisory Nuget
|
||||||
|
value:
|
||||||
|
Name: "GitHub Security Advisory Nuget"
|
||||||
|
URL: "https://github.com/advisories?query=type%%3Areviewed+ecosystem%%3Anuget"
|
||||||
@@ -5,7 +5,6 @@ import (
|
|||||||
|
|
||||||
"golang.org/x/xerrors"
|
"golang.org/x/xerrors"
|
||||||
|
|
||||||
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
|
||||||
"github.com/aquasecurity/trivy-db/pkg/vulnsrc/node"
|
"github.com/aquasecurity/trivy-db/pkg/vulnsrc/node"
|
||||||
"github.com/aquasecurity/trivy/pkg/types"
|
"github.com/aquasecurity/trivy/pkg/types"
|
||||||
)
|
)
|
||||||
@@ -33,8 +32,7 @@ func (a *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
|
|
||||||
var vulns []types.DetectedVulnerability
|
var vulns []types.DetectedVulnerability
|
||||||
for _, advisory := range advisories {
|
for _, advisory := range advisories {
|
||||||
adv := convertToGenericAdvisory(advisory)
|
if !a.comparer.IsVulnerable(pkgVer, advisory) {
|
||||||
if !a.comparer.IsVulnerable(pkgVer, adv) {
|
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -43,30 +41,16 @@ func (a *Advisory) DetectVulnerabilities(pkgName, pkgVer string) ([]types.Detect
|
|||||||
PkgName: pkgName,
|
PkgName: pkgName,
|
||||||
InstalledVersion: pkgVer,
|
InstalledVersion: pkgVer,
|
||||||
FixedVersion: createFixedVersions(advisory.PatchedVersions),
|
FixedVersion: createFixedVersions(advisory.PatchedVersions),
|
||||||
|
DataSource: advisory.DataSource,
|
||||||
}
|
}
|
||||||
vulns = append(vulns, vuln)
|
vulns = append(vulns, vuln)
|
||||||
}
|
}
|
||||||
return vulns, nil
|
return vulns, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func convertToGenericAdvisory(advisory node.Advisory) dbTypes.Advisory {
|
func createFixedVersions(patchedVersions []string) string {
|
||||||
var vulnerable, patched []string
|
|
||||||
if advisory.VulnerableVersions != "" {
|
|
||||||
vulnerable = strings.Split(advisory.VulnerableVersions, "||")
|
|
||||||
}
|
|
||||||
if advisory.PatchedVersions != "" {
|
|
||||||
patched = strings.Split(advisory.PatchedVersions, "||")
|
|
||||||
}
|
|
||||||
|
|
||||||
return dbTypes.Advisory{
|
|
||||||
VulnerableVersions: vulnerable,
|
|
||||||
PatchedVersions: patched,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func createFixedVersions(patchedVersions string) string {
|
|
||||||
var fixedVersions []string
|
var fixedVersions []string
|
||||||
for _, s := range strings.Split(patchedVersions, "||") {
|
for _, s := range patchedVersions {
|
||||||
fixedVersions = append(fixedVersions, strings.TrimSpace(s))
|
fixedVersions = append(fixedVersions, strings.TrimSpace(s))
|
||||||
}
|
}
|
||||||
return strings.Join(fixedVersions, ", ")
|
return strings.Join(fixedVersions, ", ")
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import (
|
|||||||
"github.com/stretchr/testify/require"
|
"github.com/stretchr/testify/require"
|
||||||
|
|
||||||
"github.com/aquasecurity/trivy-db/pkg/db"
|
"github.com/aquasecurity/trivy-db/pkg/db"
|
||||||
|
dbTypes "github.com/aquasecurity/trivy-db/pkg/types"
|
||||||
"github.com/aquasecurity/trivy/pkg/dbtest"
|
"github.com/aquasecurity/trivy/pkg/dbtest"
|
||||||
"github.com/aquasecurity/trivy/pkg/detector/library/npm"
|
"github.com/aquasecurity/trivy/pkg/detector/library/npm"
|
||||||
"github.com/aquasecurity/trivy/pkg/types"
|
"github.com/aquasecurity/trivy/pkg/types"
|
||||||
@@ -30,13 +31,20 @@ func TestAdvisory_DetectVulnerabilities(t *testing.T) {
|
|||||||
pkgName: "electron",
|
pkgName: "electron",
|
||||||
pkgVer: "2.0.17",
|
pkgVer: "2.0.17",
|
||||||
},
|
},
|
||||||
fixtures: []string{"testdata/fixtures/npm.yaml"},
|
fixtures: []string{
|
||||||
|
"testdata/fixtures/npm.yaml",
|
||||||
|
"testdata/fixtures/data-source.yaml",
|
||||||
|
},
|
||||||
want: []types.DetectedVulnerability{
|
want: []types.DetectedVulnerability{
|
||||||
{
|
{
|
||||||
PkgName: "electron",
|
PkgName: "electron",
|
||||||
InstalledVersion: "2.0.17",
|
InstalledVersion: "2.0.17",
|
||||||
VulnerabilityID: "CVE-2019-5786",
|
VulnerabilityID: "CVE-2019-5786",
|
||||||
FixedVersion: "^2.0.18, ^3.0.16, ^3.1.6, ^4.0.8, ^5.0.0-beta.5",
|
FixedVersion: "^2.0.18, ^3.0.16, ^3.1.6, ^4.0.8, ^5.0.0-beta.5",
|
||||||
|
DataSource: &dbTypes.DataSource{
|
||||||
|
Name: "Node.js Ecosystem Security Working Group",
|
||||||
|
URL: "https://github.com/nodejs/security-wg",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@@ -79,10 +87,9 @@ func TestAdvisory_DetectVulnerabilities(t *testing.T) {
|
|||||||
require.NotNil(t, err)
|
require.NotNil(t, err)
|
||||||
assert.Contains(t, err.Error(), tt.wantErr)
|
assert.Contains(t, err.Error(), tt.wantErr)
|
||||||
return
|
return
|
||||||
} else {
|
|
||||||
assert.NoError(t, err)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
assert.NoError(t, err)
|
||||||
assert.Equal(t, tt.want, got)
|
assert.Equal(t, tt.want, got)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
6
pkg/detector/library/npm/testdata/fixtures/data-source.yaml
vendored
Normal file
6
pkg/detector/library/npm/testdata/fixtures/data-source.yaml
vendored
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
- bucket: data-source
|
||||||
|
pairs:
|
||||||
|
- key: nodejs-security-wg
|
||||||
|
value:
|
||||||
|
Name: "Node.js Ecosystem Security Working Group"
|
||||||
|
URL: "https://github.com/nodejs/security-wg"
|
||||||
@@ -4,5 +4,15 @@
|
|||||||
pairs:
|
pairs:
|
||||||
- key: CVE-2019-5786
|
- key: CVE-2019-5786
|
||||||
value:
|
value:
|
||||||
PatchedVersions: "^2.0.18 || ^3.0.16 || ^3.1.6 || ^4.0.8 || ^5.0.0-beta.5"
|
PatchedVersions:
|
||||||
VulnerableVersions: "<2.0.18 || <3.0.16 || <3.1.6 || <4.0.8 || <5.0.0-beta.5"
|
- "^2.0.18"
|
||||||
|
- "^3.0.16"
|
||||||
|
- "^3.1.6"
|
||||||
|
- "^4.0.8"
|
||||||
|
- "^5.0.0-beta.5"
|
||||||
|
VulnerableVersions:
|
||||||
|
- "<2.0.18"
|
||||||
|
- "<3.0.16"
|
||||||
|
- "<3.1.6"
|
||||||
|
- "<4.0.8"
|
||||||
|
- "<5.0.0-beta.5"
|
||||||
|
|||||||
14
pkg/detector/library/testdata/fixtures/data-source.yaml
vendored
Normal file
14
pkg/detector/library/testdata/fixtures/data-source.yaml
vendored
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
- bucket: data-source
|
||||||
|
pairs:
|
||||||
|
- key: composer::GitLab Advisory Database Community
|
||||||
|
value:
|
||||||
|
Name: "GitLab Advisory Database Community"
|
||||||
|
URL: "https://gitlab.com/gitlab-org/advisories-community"
|
||||||
|
- key: composer::php-security-advisories
|
||||||
|
value:
|
||||||
|
Name: "PHP Security Advisories Database"
|
||||||
|
URL: "https://github.com/FriendsOfPHP/security-advisories"
|
||||||
|
- key: rubygems::ruby-advisory-db
|
||||||
|
value:
|
||||||
|
Name: "Ruby Advisory Database"
|
||||||
|
URL: "https://github.com/rubysec/ruby-advisory-db"
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
- bucket: "composer::GitHub Security Advisory Composer"
|
- bucket: "composer::GitLab Advisory Database Community"
|
||||||
pairs:
|
pairs:
|
||||||
- bucket: symfony/symfony
|
- bucket: symfony/symfony
|
||||||
pairs:
|
pairs:
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
- bucket: "GitHub Security Advisory Rubygems"
|
- bucket: "GitHub Security Advisory RubyGems"
|
||||||
pairs:
|
pairs:
|
||||||
- bucket: rails
|
- bucket: rails
|
||||||
pairs:
|
pairs:
|
||||||
|
|||||||
@@ -17,6 +17,9 @@ type DetectedVulnerability struct {
|
|||||||
SeveritySource string `json:",omitempty"`
|
SeveritySource string `json:",omitempty"`
|
||||||
PrimaryURL string `json:",omitempty"`
|
PrimaryURL string `json:",omitempty"`
|
||||||
|
|
||||||
|
// DataSource holds where the advisory comes from
|
||||||
|
DataSource *types.DataSource `json:",omitempty"`
|
||||||
|
|
||||||
// Custom is for extensibility and not supposed to be used in OSS
|
// Custom is for extensibility and not supposed to be used in OSS
|
||||||
Custom interface{} `json:",omitempty"`
|
Custom interface{} `json:",omitempty"`
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user