You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
When the scanned resource is a Deployment-managed Pod, resource_name is the ReplicaSet name, which changes on every deploy (new hash suffix). Since close_old_findings scopes its query by exact service match:
...every reimport after a new deploy uses a brand-new service value, so close_old_findings can never see (and therefore never close) findings created by any previous deploy generation. Findings only ever accumulate; nothing is ever mitigated by reimport for this scan type, regardless of close_old_findings=true.
This is the same underlying pattern already discussed in #11500, where a maintainer clarified that service is meant to be a stable identifier chosen by the caller, and reimports will only close old findings correctly "as long as you don't include a version number and the value stays the same across reimports." That guidance is correct for callers building their own service value via the API — but here the violation is happening inside DefectDojo's own bundled parser, not in caller-supplied input. Nothing in the trivy-dojo-report-operator integration (or any other caller of /api/v2/reimport-scan/ for this scan type) has the ability to override this, since the parser derives and sets service itself from the report content.
Impact observed in production
Over ~3 months, one dojo_finding table grew from ~218k to 5.7M+ rows for Kubernetes workloads scanned via Trivy Operator across 8 clusters, because no finding from a prior deploy generation was ever closed automatically — only ever added to. This directly degraded Postgres performance (large table + index footprint) enough to cause dashboard timeouts and an availability incident, on top of requiring recurring manual SQL cleanup as a workaround.
Steps to reproduce
Deploy a workload managed by a Deployment (so its Pods belong to a ReplicaSet) in Kubernetes.
Scan it with the Trivy Operator and reimport the VulnerabilityReport into DefectDojo via /api/v2/reimport-scan/ with scan_type=Trivy Operator Scan, close_old_findings=true.
Trigger a new deploy (new ReplicaSet, e.g. any rolling update) and reimport the new scan for the same workload/engagement.
Observe: findings from the first scan remain active, even for CVEs no longer present in the new scan / already fixed. Finding.service differs between the two Tests (different ReplicaSet name embedded).
Expected behavior
close_old_findings should be able to recognize that both reimports are for the same logical Kubernetes workload, and close findings that are genuinely no longer present. At minimum, the bundled Trivy Operator parser should not embed a value that's expected to change on every reimport (ReplicaSet name) into a field (service) whose entire purpose is to stay stable across reimports.
Suggested fixes (any of)
Drop resource_name (or just the ReplicaSet-generated suffix) from the service string built in vulnerability_handler.py, keeping only namespace/kind/container (or similar stable identity).
Expose this as a configurable behavior for the Trivy Operator parser, similar to how DD_HASHCODE_FIELDS_PER_SCANNER lets users override deduplication hash fields per parser (see trivy operator scan: deduplication is not working #12320) — but for service construction.
Document, in the same place service's stability requirement is documented (per the discussion in Issue with closing of old findings for upgraded image #11500), that scanner parsers bundled with DefectDojo are also expected to honor this contract, since users have no way to override parser-internal service construction today.
trivy operator scan: deduplication is not working #12320 (separate but related Trivy Operator Scan dedup issue, same root cause class: parser embeds a per-deploy-volatile Kubernetes identifier into a field expected to stay stable across reimports — there it was description/hash, here it's service)
Bug description
The bundled "Trivy Operator Scan" parser builds
Finding.servicefrom the scanned resource's identity, including the Kubernetes object name:(
dojo/tools/trivy_operator/vulnerability_handler.py)When the scanned resource is a Deployment-managed Pod,
resource_nameis the ReplicaSet name, which changes on every deploy (new hash suffix). Sinceclose_old_findingsscopes its query by exactservicematch:(
dojo/importers/default_importer.py)...every reimport after a new deploy uses a brand-new
servicevalue, soclose_old_findingscan never see (and therefore never close) findings created by any previous deploy generation. Findings only ever accumulate; nothing is ever mitigated by reimport for this scan type, regardless ofclose_old_findings=true.This is the same underlying pattern already discussed in #11500, where a maintainer clarified that
serviceis meant to be a stable identifier chosen by the caller, and reimports will only close old findings correctly "as long as you don't include a version number and the value stays the same across reimports." That guidance is correct for callers building their ownservicevalue via the API — but here the violation is happening inside DefectDojo's own bundled parser, not in caller-supplied input. Nothing in thetrivy-dojo-report-operatorintegration (or any other caller of/api/v2/reimport-scan/for this scan type) has the ability to override this, since the parser derives and setsserviceitself from the report content.Impact observed in production
Over ~3 months, one
dojo_findingtable grew from ~218k to 5.7M+ rows for Kubernetes workloads scanned via Trivy Operator across 8 clusters, because no finding from a prior deploy generation was ever closed automatically — only ever added to. This directly degraded Postgres performance (large table + index footprint) enough to cause dashboard timeouts and an availability incident, on top of requiring recurring manual SQL cleanup as a workaround.Steps to reproduce
VulnerabilityReportinto DefectDojo via/api/v2/reimport-scan/withscan_type=Trivy Operator Scan,close_old_findings=true.active, even for CVEs no longer present in the new scan / already fixed.Finding.servicediffers between the twoTests (different ReplicaSet name embedded).Expected behavior
close_old_findingsshould be able to recognize that both reimports are for the same logical Kubernetes workload, and close findings that are genuinely no longer present. At minimum, the bundled Trivy Operator parser should not embed a value that's expected to change on every reimport (ReplicaSet name) into a field (service) whose entire purpose is to stay stable across reimports.Suggested fixes (any of)
resource_name(or just the ReplicaSet-generated suffix) from theservicestring built invulnerability_handler.py, keeping onlynamespace/kind/container(or similar stable identity).DD_HASHCODE_FIELDS_PER_SCANNERlets users override deduplication hash fields per parser (see trivy operator scan: deduplication is not working #12320) — but forserviceconstruction.service's stability requirement is documented (per the discussion in Issue with closing of old findings for upgraded image #11500), that scanner parsers bundled with DefectDojo are also expected to honor this contract, since users have no way to override parser-internalserviceconstruction today.Deployment method
Environment information
telekom-mms/trivy-dojo-report-operator→/api/v2/reimport-scan/,scan_type=Trivy Operator ScanRelated
service-stability pattern, but caller-suppliedservicerather than parser-internal)description/hash, here it'sservice)