The platform hardens the node image; the images your workloads pull are yours to check. Scan them for known CVEs with Trivy or Grype, twice: in CI before an image is pushed, and again inside the cluster, because vulnerabilities are found after an image is built. Then gate admission so a critically vulnerable image cannot run. ## Scan in CI, before push The cheapest place to catch a vulnerable image is before it exists in your registry. Add a scan step to the pipeline that builds it: ```console $ trivy image --severity HIGH,CRITICAL --exit-code 1 registry.example.com/team/app:1.4.0 ``` `--exit-code 1` fails the build on a finding at the chosen severity, so a vulnerable image never gets pushed. Grype does the same with `grype --fail-on high`. ## Scan again inside the cluster An image that was clean at build time accumulates CVEs as new ones are disclosed against its packages. Run recurring scans in the cluster so you catch a newly disclosed vulnerability in an image you already run. An operator pattern (for example Trivy Operator) scans every workload's images on a schedule and writes the results as Kubernetes objects you can query and alert on. ## Read a report A report lists more than a CVE id; use the fields to triage: - **CVSS** is the severity score, the first cut. - **EPSS** estimates the probability the CVE is exploited in the wild, which separates a CVE that is only bad in theory from one that attackers actually use. - **KEV** (the CISA Known Exploited Vulnerabilities catalog) flags CVEs seen exploited, the ones to fix first. - **Fixed version** tells you whether an upgrade even exists yet. Prioritize KEV and high-EPSS findings with a fixed version; a high CVSS with no fix and no exploitation is a lower priority than the number alone suggests. ## Honor the platform's VEX verdicts For the node image, Syself ships VEX (Vulnerability Exploitability eXchange) statements that say which CVEs actually apply and which are not exploitable in the image's configuration; see [Security evidence a release produces](/docs/hetzner/apalla/security/security-evidence-per-release). Feed those VEX statements to your scanner so its results match the platform's triage, and you do not chase a CVE the platform has already assessed as not applicable. ## Gate admission on severity Turn the scan into a rule: block an image with a critical, fixable CVE from running. Do this with a policy engine ([Kyverno](/docs/hetzner/apalla/security/use-kyverno-policies) or Gatekeeper), gating on the scan result. Roll it out audit-first, so you see what would be blocked before you block it, then enforce. ## How this differs from the node-image SBOM Scanning your workload images is a different job from the platform's own [supply-chain evidence](/docs/hetzner/apalla/security/supply-chain-security): that SBOM covers the node OS Syself builds, this covers the application images you choose and pull. You need both, and this side is yours. ## Related - [Verify image signatures](/docs/hetzner/apalla/security/verify-image-signatures): require signed images at admission, alongside scanning them. - [Security evidence a release produces](/docs/hetzner/apalla/security/security-evidence-per-release): the SBOM and VEX verdicts to feed your scanner so its results match the platform's triage. - [Supply-chain security](/docs/hetzner/apalla/security/supply-chain-security): how Syself pins and scans the node image itself. - [Runtime threat detection](/docs/hetzner/apalla/security/runtime-threat-detection): catch at runtime what a scan before deployment cannot.