anchore/grype
Risk prioritization
Purpose
Most scans return more vulnerabilities than a team can act on. Grype layers several signals to help prioritize:
- CVSS — the canonical severity number, parsed by
pandatix/go-cvss. - EPSS — daily-updated exploit prediction probabilities.
- CISA KEV — boolean "actively exploited" flag from CISA.
- Risk score — a derived single number combining the above.
- Severity gating —
--fail-onexits with code 2 when any match meets a threshold.
The data is loaded from vulnerability.db via the decorator store and surfaced in the JSON output.
Decorator store
grype/db/v6/vulnerability_decorator_store.go holds KEV and EPSS data keyed by vulnerability ID:
- CISA KEV: source URL, date added, "known ransomware campaign use" flag.
- EPSS: probability of exploitation in the next 30 days, percentile, computed-on date.
The decorator store is read in lockstep with the vulnerability provider — every vulnerability returned through vulnerability.Provider carries its decoration if available.
The schema additions that introduced KEV and EPSS bumped the v6 Addition counter:
6.0.1— KEV.6.0.2— EPSS.
(See grype/db/v6/db.go for the full changelog.)
Severity classification
grype/vulnerability/severity.go defines the canonical severity enum:
type Severity int
const (
UnknownSeverity Severity = iota
NegligibleSeverity
LowSeverity
MediumSeverity
HighSeverity
CriticalSeverity
)ParseSeverity(string) is forgiving — it normalizes "HIGH", "high", "High", and "important" to HighSeverity. The same enum is used for CVSS and for distro-specific severities (which often differ).
--fail-on
When --fail-on <severity> is set:
if m.FailSeverity != nil && hasSeverityAtOrAbove(m.VulnerabilityProvider, *m.FailSeverity, *remainingMatches) {
err = grypeerr.ErrAboveSeverityThreshold
}hasSeverityAtOrAbove (in grype/vulnerability_matcher.go) consults the metadata provider for each match and returns true the moment one meets or exceeds the threshold. The CLI maps ErrAboveSeverityThreshold to exit code 2, which CI systems use to gate merges.
--by-cve normalization
When grouping for prioritization or deduplication, having every vulnerability use the same identifier matters. --by-cve rewrites advisory IDs (RHSA, GHSA, DSA, USN) to their CVE form when the vulnerability record carries one in RelatedVulnerabilities. See Matcher system.
EOL distro warnings
If --alerts.enable-eol-distro-warnings is set, the matcher pipeline tracks packages from end-of-life distros via vulnerability_matcher.go::eolTracker. The provider must implement the optional vulnerability.EOLChecker interface; v6 does. EOL distros surface as a separate alert in the output, distinct from per-vulnerability findings.
Output surfaces
- Table — severity column with color (red for critical, etc.).
- JSON — every match has a
vulnerability.severityfield plus optionalcvss,kev, andepssblocks. - SARIF — severity is mapped to SARIF level; KEV/EPSS appear as additional properties.
- CycloneDX — vulnerabilities carry CVSS and other ratings inline.
Key source files
| File | Purpose |
|---|---|
grype/db/v6/vulnerability_decorator_store.go |
KEV + EPSS data store. |
grype/vulnerability/severity.go |
Severity enum + parsing. |
grype/vulnerability_matcher.go (hasSeverityAtOrAbove) |
--fail-on evaluation. |
grype/grypeerr/ |
Sentinel errors mapped to exit codes. |
grype/presenter/models/ |
JSON shape including KEV/EPSS fields. |
Entry points for modification
- Add a new prioritization signal — extend the decorator store with a new field, bump the
Additioncounter, populate it during DB build, and surface it in the JSON model and presenters. - Change risk scoring — locate the score derivation (currently a function of CVSS + KEV + EPSS) and adjust; consider whether the change is backward-compatible for downstream consumers reading the JSON output.
Built by Factory AutoWiki from public repository content. It is a generated preview for codebase exploration, not source-maintained documentation.