statnett/image-scanner-operator

GitHub: statnett/image-scanner-operator

Kubernetes Operator 用于检测运行中容器镜像的漏洞,弥补流水线扫描无法覆盖已上线工作负载的盲区。

Stars: 33 | Forks: 10

# Image Scanner Operator [![Conventional Commits](https://img.shields.io/badge/Conventional%20Commits-1.0.0-%23FE5196?logo=conventionalcommits&logoColor=white)][conventional-commits] [![Go Report Card](https://goreportcard.com/badge/github.com/statnett/image-scanner-operator)][report-card] [![CodeQL](https://static.pigsec.cn/wp-content/uploads/repos/2026/04/c395c29989212935.svg)][CodeQL] Image Scanner 是一个支持检测运行中容器镜像漏洞的 Kubernetes Operator。 Kubernetes 集群运行的容器源自来源多样的容器镜像。 有些镜像是为内部应用定制的,而另一些则是从内部/外部 registry 拉取的。 在容器镜像构建流水线中扫描镜像被视为最佳实践,以便向开发者提供关于潜在漏洞的早期反馈。 虽然这很好,但这还不够: 软件漏洞通常在软件可供使用后才被检测到,而一些应用通常会在其运行时环境中“仅仅运行”——很少或根本没有维护。 而且有些用户可能根本不使用流水线,或者使用未启用镜像扫描的流水线。 在包含漏洞的容器镜像上运行应用程序_可能_代表一种不可接受的威胁。 为了解决这个问题,我们需要**一种识别运行中容器镜像漏洞的机制**。 然后,开发者、系统管理员、平台管理员和安全官员可以使用此机制 在检测到漏洞时采取行动。 行动例如可以是: - 升级到易受攻击软件组件的修补版本 - 得出漏洞不相关的结论 - 得出漏洞代表可接受风险的结论 - 关闭应用程序 似乎有很多公司/社区提供类似的软件。此 operator 的一些关键特性是: - **可配置为扫描任何 [Kubernetes Workload](https://kubernetes.io/docs/concepts/workloads/) 的容器镜像**, 包括自定义资源。唯一的要求是资源必须 [拥有](https://kubernetes.io/docs/concepts/overview/working-with-objects/owners-dependents/) Pod——无论是直接还是间接。 - **容器镜像基于从 [Container Runtime Interface (CRI)](https://kubernetes.io/docs/concepts/architecture/cri/) 获取的不可变镜像 sha256 digest 进行扫描**, 而不是基于可能可变的镜像 tag。 - 为避免不必要的镜像拉取,镜像扫描 workload 最好调度在与待扫描 workload 相同的节点上。 - 由于待扫描的镜像应该已经存在于节点容器 registry 中,**镜像扫描 workload 不必为私有镜像处理镜像拉取 secret**,利用了一个 [Kubernetes "bug"](https://github.com/kubernetes/kubernetes/issues/18787)。 ## Description // TODO(user): 关于您的项目和概述的深入段落 ### Custom resources Image Scanner operator 目前定义了面向用户的单一自定义资源定义 (CRD),即 [ContainerImageScan][CIS-CRD] (CIS),它代表了 workload 容器镜像运行时镜像扫描的 Kubernetes API。 有关 CIS 资源的(简化)示例,请参见 [stas_v1alpha1_containerimagescan.yaml][CIS-example]。 CIS 资源 `.spec` 指定要扫描的容器镜像和一些额外的 workload 元数据,镜像扫描结果的摘要由 `ContainerImageScan` controller 在 `.status` 中添加/更新。 检测到的漏洞的详细报告发布到由 CIS 拥有的 [OpenReports](https://openreports.io/) `Report` 资源中。 有关 Image Scanner operator 管理的 `Report` 资源示例,请参见 [v1alpha1_report.yaml][Report-example]。 标准用户不应编辑 CIS 资源,因为 `Workload` controller 将从运行中的 pod 创建 CIS 资源。并且当拥有 pod 消失时,标准 Kubernetes 垃圾收集器会删除过时的 CIS 资源。 用户可以通过向 pod 添加 annotation 来影响镜像扫描过程。 annotation 集合目前有限,但未来可能会添加更多: | Pod annotation key | Default value | Description | |--------------------------------------------|:--------------|:----------------------------------------------------------------------------------------------------------------------| | `image-scanner.statnett.no/ignore-unfixed` | `"false"` | If set to `"true"`, the Image Scanner will ignore any detected vulnerability that can't be fix by updating package(s) | ### Supported features - Namespaced 容器镜像扫描 API (custom resource): `ContainerImageScan` (CIS) - CIS 资源包含已检测漏洞的详细信息和摘要 - 用户可以识别已扫描容器镜像的拥有/控制资源 (workload) - 所有容器镜像都会定期重新扫描,间隔可配置 - 提供 CIS 的漏洞摘要指标以启用仪表板/警报 - 任何有权访问 namespace 的用户都被允许_查看_ CIS - Cluster-scoped operator,在配置的 namespace 中运行,具有应扫描的 namespace 的包含/阻止列表 - 通过配置支持任何类型的 workload(也包括 CRD) - 扫描来自私有/认证镜像 registry 的 workload 镜像 ### Future improvements - 向利益相关者推送反馈 - 允许用户忽略/抑制漏洞 - 根据检测到的漏洞执行操作 ### Eschewed Features - 生成漏洞详情指标 - 历史容器镜像扫描 - Helm chart 安装 ## Getting Started 您需要一个 Kubernetes 集群来运行 Image Scanner。 您可以使用 [KIND](https://sigs.k8s.io/kind) 或 [k3s](https://k3s.io/) 来获取用于测试的本地集群。 我们目前仅支持使用 [Kustomize](https://kustomize.io/) 进行安装, 无论是作为独立工具, 使用 `kubectl` 最新版本中的 kustomize (`-k`) 功能, 还是任何支持 Kustomize 的 GitOps 工具。 ### Prerequisites 在安装 Image Scanner operator 之前,OpenReports CRD 必须存在于集群中。 如果您正在使用 [Kyverno](https://kyverno.io/),OpenReports CRD 可能已经安装。从 Kyverno 1.15 版本(Helm chart 3.5)开始,有一个选择性加入 (opt-in) 选项可以让 Kyverno 以 OpenReports 格式生成报告。要启用该选项, 请设置 Kyverno Helm chart 值 `openreports.enable=true`,这将确保所需的 CRD 由 Kyverno Helm chart 安装。 如果您没有使用 Kyverno,可以使用上游 [OpenReports Helm chart](https://github.com/openreports/reports-api/pkgs/container/charts%2Fopenreports) 安装 OpenReports CRD。 ``` helm install oci://ghcr.io/openreports/charts/openreports ``` ### Install 由于您可能希望调整默认配置(和/或拥有多个集群),我们建议您首先使用 Image Scanner 默认 kustomization 作为 [remote directory](https://github.com/kubernetes-sigs/kustomize/blob/master/examples/remoteBuild.md#remote-directories) base 来创建 kustomize overlay。您最初的 kustomization.yaml 可以很简单: ``` resources: - https://github.com/statnett/image-scanner-operator?ref=v0.16.13 ``` 如果您有多个集群,则应为每个集群创建一个 [variant](https://kubectl.docs.kubernetes.io/references/kustomize/glossary/#variant) overlay。 要将 operator 安装(或更新)到您的集群中,请运行: ``` kubectl apply --server-side -k ``` ### Configure Image Scanner operator 高度可配置,并支持带有相应环境变量的众多 flag。要概览所有可配置的内容,最简单的方法是使用 CLI: ``` docker run ghcr.io/statnett/image-scanner-operator --help ``` 您也可以使用环境变量进行配置,但 flag 优先于相应的环境变量。 环境变量名称可以通过大写并将 `-` 分隔符替换为 `_` 从 flag 推断出来。 由于我们使用 kustomize 安装 operator,最简单的方法是 使用 [configMapGenerator](https://kubectl.docs.kubernetes.io/references/kustomize/kustomization/configmapgenerator/) 从默认 Image Scanner 配置中的 ConfigMap 定制提供的环境变量。 ``` configMapGenerator: - name: image-scanner-config behavior: merge literals: - CIS_METRICS_LABELS=app.kubernetes.io/name - SCAN_INTERVAL=24h ``` 此示例将覆盖默认配置为: - 添加从 `app.kubernetes.io/name` Pod label 获取值的 metric label - 以 24 小时的间隔重新扫描 workload 镜像 #### Configure Trivy scan jobs workload 容器镜像通过调度运行在扫描目标容器镜像上的 Kubernetes _Job_ 进行扫描。使用 job 容器内的 [`trivy filesystem`](https://aquasecurity.github.io/trivy/latest/docs/references/configuration/cli/trivy_filesystem/) 命令扫描镜像。 `trivy filesystem` 扫描命令可以通过修改 `trivy-job-config` _ConfigMap_ 进行自定义。_ConfigMap_ 中的所有条目都作为带有 `TRIVY_` 前缀的环境变量挂载——这将允许 Trivy 选取它们。示例: ``` - name: trivy-job-config namespace: image-scanner behavior: merge literals: - DB_REPOSITORY=/aquasecurity/trivy-db - JAVA_DB_REPOSITORY=/aquasecurity/trivy-java-db - OFFLINE_SCAN=true # enabling offline mode for air-gapped environments ``` ### Upgrade 在这个早期阶段,我们可能会引入破坏性变更。但当我们这样做时, 破坏性变更应在 changelog 和 release notes 中突出显示。 我们也可能对 CRD 进行破坏性更改,而不增加转换 webhook 的复杂性。因此,如果您在升级到更新版本时遇到任何问题,请首先尝试重新安装 operator。 ### Uninstall 要卸载 operator,只需使用 `kubectl` 删除 [安装](#install) operator 时 overlay 生成的所有资源: ``` kubectl delete -k --ignore-not-found=true ``` ### How it works 该项目旨在遵循 Kubernetes [Operator pattern](https://kubernetes.io/docs/concepts/extend-kubernetes/operator/)。 它使用 [Controllers](https://kubernetes.io/docs/concepts/architecture/controller/) ,它提供一个 reconcile 函数,负责同步资源 直到达到所需状态。 Image Scanner 由三个 controller 组成,它们协调 运行中容器镜像的扫描,如下图所示。 容器镜像扫描 Kubernetes API 由 `ContainerImageScan` 自定义资源实体化, 在其 status 中提供最终一致的镜像扫描摘要。 容器镜像的实际漏洞扫描和漏洞数据库由 operator 的外部服务提供。 使用一个简单的 `Pod`(带有单个容器)作为示例: 1. 当 `Pod` status 中存在不可变镜像引用时,创建一个 `ContainerImageScan`。 2. 从 `ContainerImageScan` spec 中的不可变镜像引用创建一个扫描 `Job`。 3. 当扫描 `Job` 完成后,从扫描 `Job` 的 pod log 读取扫描结果, 并更新 `ContainerImageScan` status。创建/更新包含已检测漏洞详情的 `Report` 资源。 4. 当 `Pod` 被删除时,`ContainerImageScan` 和 `Report` 被垃圾回收。 ![Image scanner component diagram](http://www.plantuml.com/plantuml/proxy?cache=no&src=https://raw.githubusercontent.com/statnett/image-scanner-operator/main/docs/operator-component.puml)) ![Scan image sequence diagram](http://www.plantuml.com/plantuml/proxy?cache=no&src=https://raw.githubusercontent.com/statnett/image-scanner-operator/main/docs/scan-sequence.puml) ## License Licensed under the [MIT License](LICENSE).
标签:Claude, CVE检测, DevSecOps, EVTX分析, Go, K8s工具, Operator, Ruby工具, Web截图, 上游代理, 子域名突变, 安全合规, 容器安全, 日志审计, 活动识别, 网络代理, 镜像扫描, 镜像漏洞