容器扫描
- Tier: 基础版,专业版,旗舰版
- Offering: JihuLab.com, 私有化部署
History
- 在极狐GitLab 15.0 中,分析器主版本从 4 更改为 5。
- 在极狐GitLab 15.0 中,从旗舰版移动至基础版。
- 引用 Docker 的容器扫描变量在极狐GitLab 15.4 中进行了重命名。
- 在极狐GitLab 15.6 中,模板从 Security/Container-Scanning.gitlab-ci.yml 移动到 Jobs/Container-Scanning.gitlab-ci.yml。
安全漏洞在容器镜像中会在整个应用生命周期中带来风险。容器扫描可以在这些风险进入生产环境之前检测到它们。当漏洞出现在您的基础镜像或操作系统的软件包中时,容器扫描会识别它们并提供解决方案路径。
- 入门教程请参见扫描 Docker 容器的漏洞。
容器扫描通常被认为是软件组成分析 (SCA) 的一部分。SCA 可以包含检查代码使用的项目的方面。这些项目通常包括应用程序和系统依赖项,几乎总是从外部来源导入,而不是从您自己编写的项目中获取。
极狐GitLab 提供容器扫描和依赖项扫描以确保涵盖所有这些依赖项类型。为了尽可能覆盖您的风险区域,我们建议您使用所有安全扫描仪。有关这些功能的比较,请参见依赖项扫描与容器扫描比较。
极狐GitLab 与 Trivy 安全扫描仪集成以执行容器中的漏洞静态分析。
Grype 分析器不再维护。现有 Grype 分析器镜像的当前主要版本将继续更新最新的咨询数据库和操作系统软件包,直到极狐GitLab 19.0,此时分析器将停止工作。
极狐GitLab 在源分支和目标分支之间比较发现的漏洞,然后:
- 在合并请求小部件中显示结果。
- 将结果保存为容器扫描报告产物,您可以下载并稍后分析。下载时,您始终会收到最新的产物。
- 保存 CycloneDX SBOM JSON 报告,列出了检测到的组件。
功能
功能 | 在基础版和专业版中 | 在旗舰版中 |
---|---|---|
自定义设置(变量、覆盖、离线环境支持等) | 是 | 是 |
作为 CI 作业产物查看 JSON 报告 | 是 | 是 |
作为 CI 作业产物生成 CycloneDX SBOM JSON 报告 | 是 | 是 |
能够通过极狐GitLab UI 中的 MR 启用容器扫描 | 是 | 是 |
UBI 镜像支持 | 是 | 是 |
支持 Trivy | 是 | 是 |
包含极狐GitLab 咨询数据库 | 限于极狐GitLab advisories-communities 项目的内容延迟 | 是 - 所有来自 Gemnasium DB 的最新内容 |
在合并请求和 CI 流水线作业的安全选项卡中显示报告数据 | 否 | 是 |
漏洞解决方案(自动修复) | 否 | 是 |
支持 漏洞允许列表 | 否 | 是 |
访问依赖项列表页面 | 否 | 是 |
配置
在您的 CI/CD 流水线中启用容器扫描分析器。流水线运行时,会扫描应用依赖的镜像是否存在漏洞。您可以使用 CI/CD 变量自定义容器扫描。
启用分析器
前提条件:
- .gitlab-ci.yml 文件中需要测试阶段。
- 使用私有化部署 runner 时,您需要使用 docker 或 kubernetes 执行器的极狐GitLab Runner 在 Linux/amd64 上。如果您使用 JihuLab.com 上的实例 runner,这是默认启用的。
- 与支持的发行版匹配的镜像。
- 构建并推送 Docker 镜像到项目的容器镜像仓库。
- 如果您使用的是第三方容器镜像仓库,可能需要通过 CS_REGISTRY_USER 和 CS_REGISTRY_PASSWORD 配置变量提供认证凭据。有关如何使用这些变量的详细信息,请参见认证到远程镜像仓库。
要启用分析器,可以:
- 启用自动 DevOps,其中包括依赖项扫描。
- 使用预配置的合并请求。
- 创建一个扫描执行策略,强制进行容器扫描。
- 手动编辑 .gitlab-ci.yml 文件。
使用预配置的合并请求
此方法会自动准备一个包含容器扫描模板的合并请求在 .gitlab-ci.yml 文件中。然后合并合并请求以启用依赖项扫描。
此方法在没有现有 .gitlab-ci.yml 文件或使用最小配置文件时效果最佳。如果您有复杂的极狐GitLab 配置文件,可能无法成功解析,并可能发生错误。在这种情况下,请改用手动方法。
要启用容器扫描:
- 在左侧边栏中,选择搜索或前往并找到您的项目。
- 选择安全 > 安全配置。
- 在容器扫描行中选择通过合并请求进行配置。
- 选择创建合并请求。
- 审查合并请求,然后选择合并。
流水线现在包括一个容器扫描作业。
手动编辑 .gitlab-ci.yml 文件
此方法要求您手动编辑现有的 .gitlab-ci.yml 文件。如果您的极狐GitLab CI/CD 配置文件很复杂或需要使用非默认选项,请使用此方法。
要启用容器扫描:
-
在左侧边栏中,选择搜索或前往并找到您的项目。
-
选择构建 > 流水线编辑器。
-
如果不存在 .gitlab-ci.yml 文件,选择配置流水线,然后删除示例内容。
-
复制并粘贴以下内容到 .gitlab-ci.yml 文件底部。如果已经存在 include 行,只需在它下面添加 template 行。
yamlinclude: - template: Jobs/Container-Scanning.gitlab-ci.yml
-
选择验证选项卡,然后选择验证流水线。
消息模拟成功完成确认文件有效。
-
选择编辑选项卡。
-
完成字段。不要使用分支字段的默认分支。
-
选择开始一个新的合并请求并提交这些更改复选框,然后选择提交更改。
-
根据您的标准工作流完成字段,然后选择创建合并请求。
-
根据您的标准工作流审查并编辑合并请求,等待流水线通过,然后选择合并。
流水线现在包括一个容器扫描作业。
自定义分析器行为
要自定义容器扫描,请使用 CI/CD 变量。
启用详细输出
当您需要详细查看依赖项扫描作业执行的操作时启用详细输出,例如在故障排除时。
在以下示例中,包含了容器扫描模板并启用了详细输出。
yamlinclude: - template: Jobs/Container-Scanning.gitlab-ci.yml variables: SECURE_LOG_LEVEL: 'debug'
扫描远程镜像仓库中的镜像
要扫描位于项目之外的镜像仓库中的镜像,请使用以下 .gitlab-ci.yml:
yaml1include: 2 - template: Jobs/Container-Scanning.gitlab-ci.yml 3 4container_scanning: 5 variables: 6 CS_IMAGE: example.com/user/image:tag
认证到远程镜像仓库
在私有镜像仓库中扫描镜像需要认证。提供用户名在 CS_REGISTRY_USER 变量中,密码在 CS_REGISTRY_PASSWORD 配置变量中。
例如,要从 AWS 弹性容器镜像仓库中扫描镜像:
yaml1container_scanning: 2 before_script: 3 - ruby -r open-uri -e "IO.copy_stream(URI.open('https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip'), 'awscliv2.zip')" 4 - unzip awscliv2.zip 5 - sudo ./aws/install 6 - aws --version 7 - export AWS_ECR_PASSWORD=$(aws ecr get-login-password --region region) 8 9include: 10 - template: Jobs/Container-Scanning.gitlab-ci.yml 11 12variables: 13 CS_IMAGE: <aws_account_id>.dkr.ecr.<region>.amazonaws.com/<image>:<tag> 14 CS_REGISTRY_USER: AWS 15 CS_REGISTRY_PASSWORD: "$AWS_ECR_PASSWORD" 16 AWS_DEFAULT_REGION: <region>
启用 FIPS 模式时不支持认证到远程镜像仓库。
报告特定语言的发现
CS_DISABLE_LANGUAGE_VULNERABILITY_SCAN CI/CD 变量控制扫描是否报告与编程语言相关的发现。有关支持语言的更多信息,请参见 Trivy 文档中的 Language-specific Packages。
默认情况下,报告仅包括由操作系统 (OS) 软件包管理器(例如,yum、apt、apk、tdnf)管理的软件包。要在非 OS 软件包中报告安全发现,请将 CS_DISABLE_LANGUAGE_VULNERABILITY_SCAN 设置为 "false":
yaml1include: 2 - template: Jobs/Container-Scanning.gitlab-ci.yml 3 4container_scanning: 5 variables: 6 CS_DISABLE_LANGUAGE_VULNERABILITY_SCAN: "false"
启用此功能时,如果项目启用了依赖项扫描,您可能会在 漏洞报告中看到重复发现。这是因为极狐GitLab 无法自动去重不同类型扫描工具的发现。要了解哪些类型的依赖项可能会被重复,请参见依赖项扫描与容器扫描比较。
在合并请求流水线中运行作业
可用的 CI/CD 变量
要自定义容器扫描,请使用 CI/CD 变量。下表列出了特定于容器扫描的 CI/CD 变量。您还可以使用任何预定义的 CI/CD 变量。
在合并到默认分支之前在合并请求中测试极狐GitLab 分析器的自定义设置。未执行此操作可能会导致意外结果,包括大量误报。
CI/CD 变量 | 默认值 | 描述 |
---|---|---|
ADDITIONAL_CA_CERT_BUNDLE | "" | 您要信任的 CA 证书包。有关更多详细信息,请参见使用自定义 SSL CA 证书授权。 |
CI_APPLICATION_REPOSITORY | $CI_REGISTRY_IMAGE/$CI_COMMIT_REF_SLUG | 要扫描的镜像的 Docker 存储库 URL。 |
CI_APPLICATION_TAG | $CI_COMMIT_SHA | 要扫描的镜像的 Docker 存储库标签。 |
CS_ANALYZER_IMAGE | registry.gitlab.com/security-products/container-scanning:7 | 分析器的 Docker 镜像。不要使用极狐GitLab 提供的分析器镜像的 :latest 标签。 |
CS_DEFAULT_BRANCH_IMAGE | "" | 默认分支上的 CS_IMAGE 名称。有关更多详细信息,请参见设置默认分支镜像。 |
CS_DISABLE_DEPENDENCY_LIST | "false" | 在极狐GitLab 17.0 中被移除。 |
CS_DISABLE_LANGUAGE_VULNERABILITY_SCAN | "true" | 禁用扫描安装在扫描镜像中的特定语言的软件包。 |
CS_DOCKER_INSECURE | "false" | 允许使用 HTTPS 访问安全 Docker 镜像仓库而不验证证书。 |
CS_DOCKERFILE_PATH | Dockerfile | 用于生成修复方案的 Dockerfile 路径。默认情况下,扫描仪会在项目的根目录中查找名为 Dockerfile 的文件。您应该仅在 Dockerfile 位于非标准位置(例如子目录)时配置此变量。有关更多详细信息,请参见漏洞解决方案。 |
CS_IGNORE_STATUSES | "" | 强制分析器忽略指定状态的发现,以逗号分隔的列表。这些值是允许的:unknown,not_affected,affected,fixed,under_investigation,will_not_fix,fix_deferred,end_of_life。1 |
CS_IGNORE_UNFIXED | "false" | 忽略未修复的发现。忽略的发现不包括在报告中。 |
CS_IMAGE | $CI_APPLICATION_REPOSITORY:$CI_APPLICATION_TAG | 要扫描的 Docker 镜像。如果设置,此变量会覆盖 $CI_APPLICATION_REPOSITORY 和 $CI_APPLICATION_TAG 变量。 |
CS_IMAGE_SUFFIX | "" | 添加到 CS_ANALYZER_IMAGE 的后缀。如果设置为 -fips,则使用 FIPS-enabled 镜像进行扫描。有关更多详细信息,请参见 FIPS-enabled 镜像。 |
CS_QUIET | "" | 如果设置,此变量会禁用作业日志中的漏洞表输出。引入于极狐GitLab 15.1。 |
CS_REGISTRY_INSECURE | "false" | 允许访问不安全的镜像仓库(仅 HTTP)。应仅在本地测试镜像时设置为 true。适用于所有扫描仪,但镜像仓库必须在端口 80/tcp 上侦听才能使 Trivy 工作。 |
CS_REGISTRY_PASSWORD | $CI_REGISTRY_PASSWORD | 访问需要身份验证的 Docker 镜像仓库的密码。默认情况下,仅在 $CS_IMAGE 位于 $CI_REGISTRY 时设置。不支持启用 FIPS 模式时。 |
CS_REGISTRY_USER | $CI_REGISTRY_USER | 访问需要身份验证的 Docker 镜像仓库的用户名。默认情况下,仅在 $CS_IMAGE 位于 $CI_REGISTRY 时设置。不支持启用 FIPS 模式时。 |
CS_SEVERITY_THRESHOLD | UNKNOWN | 严重性水平阈值。扫描仪输出严重性水平高于或等于此阈值的漏洞。支持的级别有 UNKNOWN、LOW、MEDIUM、HIGH 和 CRITICAL。 Default value changed to MEDIUM in 极狐GitLab 17.8。 |
CS_TRIVY_JAVA_DB | "registry.gitlab.com/gitlab-org/security-products/dependencies/trivy-java-db" | 指定 trivy-java-db 漏洞数据库的备用位置。 |
CS_TRIVY_DETECTION_PRIORITY | "precise" | 使用定义的 Trivy 检测优先级进行扫描。允许的值有:precise 或 comprehensive。 |
SECURE_LOG_LEVEL | info | 设置最低日志级别。输出此日志级别或更高的消息。从最高到最低严重性,日志级别为:fatal、error、warn、info、debug。 |
TRIVY_TIMEOUT | 5m0s | 设置扫描的超时。 |
脚注:
- 修复状态信息高度依赖于软件供应商和容器镜像操作系统软件包元数据的准确修复可用性数据。它也受个别容器扫描仪的解释。在容器扫描仪错误报告漏洞的修复包可用的情况下,启用 CS_IGNORE_STATUSES 时使用此设置可能导致误报或误报过滤。
支持的发行版
支持以下 Linux 发行版:
- Alma Linux
- Alpine Linux
- Amazon Linux
- CentOS
- CBL-Mariner
- Debian
- Distroless
- Oracle Linux
- Photon OS
- Red Hat (RHEL)
- Rocky Linux
- SUSE
- Ubuntu
FIPS-enabled 镜像
极狐GitLab 还提供 FIPS-enabled Red Hat UBI 版本的容器扫描镜像。因此,您可以将标准镜像替换为 FIPS-enabled 镜像。要配置镜像,请将 CS_IMAGE_SUFFIX 设置为 -fips 或修改 CS_ANALYZER_IMAGE 变量为标准标签加上 -fips 扩展。
在极狐GitLab 实例中启用 FIPS 模式时,CS_ANALYZER_IMAGE 自动添加 -fips 标志。
启用 FIPS 模式时不支持认证镜像仓库中的镜像扫描。当 CI_GITLAB_FIPS_MODE 为 "true",并且设置了 CS_REGISTRY_USER 或 CS_REGISTRY_PASSWORD 时,分析器会退出并不执行扫描。
覆盖容器扫描模板
如果您想覆盖作业定义(例如,改变 variables 的属性),必须在模板包含后声明并覆盖作业,然后指定任何附加键。
此示例将 GIT_STRATEGY 设置为 fetch:
yaml1include: 2 - template: Jobs/Container-Scanning.gitlab-ci.yml 3 4container_scanning: 5 variables: 6 GIT_STRATEGY: fetch
设置默认分支镜像
默认情况下,容器扫描假设镜像命名约定将任何分支特定标识符存储在镜像标签中而不是镜像名称中。当镜像名称在默认分支和非默认分支之间不同时,先前检测到的漏洞会在合并请求中显示为新检测到的。
当同一个镜像在默认分支和非默认分支上有不同的名称时,您可以使用 CS_DEFAULT_BRANCH_IMAGE 变量来指示该镜像在默认分支上的名称。极狐GitLab 然后在非默认分支运行扫描时正确确定漏洞是否已经存在。
例如,假设如下:
- 非默认分支发布镜像的命名约定为 $CI_REGISTRY_IMAGE/$CI_COMMIT_BRANCH:$CI_COMMIT_SHA。
- 默认分支发布镜像的命名约定为 $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA。
在此示例中,您可以使用以下 CI/CD 配置来确保漏洞不会重复:
yaml1include: 2 - template: Jobs/Container-Scanning.gitlab-ci.yml 3 4container_scanning: 5 variables: 6 CS_DEFAULT_BRANCH_IMAGE: $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA 7 before_script: 8 - export CS_IMAGE="$CI_REGISTRY_IMAGE/$CI_COMMIT_BRANCH:$CI_COMMIT_SHA" 9 - | 10 if [ "$CI_COMMIT_BRANCH" == "$CI_DEFAULT_BRANCH" ]; then 11 export CS_IMAGE="$CI_REGISTRY_IMAGE:$CI_COMMIT_SHA" 12 fi
对于给定的 CS_IMAGE,CS_DEFAULT_BRANCH_IMAGE 应保持不变。如果它发生变化,则会创建一组重复的漏洞,必须手动驳回。
使用 Auto DevOps 时,CS_DEFAULT_BRANCH_IMAGE 自动设置为 $CI_REGISTRY_IMAGE/$CI_DEFAULT_BRANCH:$CI_APPLICATION_TAG。
使用自定义 SSL CA 证书授权
您可以使用 ADDITIONAL_CA_CERT_BUNDLE CI/CD 变量来配置自定义 SSL CA 证书授权,用于在通过 HTTPS 从镜像仓库中获取 Docker 镜像时验证对等方。ADDITIONAL_CA_CERT_BUNDLE 的值应包含 X.509 PEM 公钥证书的文本表示。例如,要在 .gitlab-ci.yml 文件中配置此值,请使用以下:
yaml1container_scanning: 2 variables: 3 ADDITIONAL_CA_CERT_BUNDLE: | 4 -----BEGIN CERTIFICATE----- 5 MIIGqTCCBJGgAwIBAgIQI7AVxxVwg2kch4d56XNdDjANBgkqhkiG9w0BAQsFADCB 6 ... 7 jWgmPqF3vUbZE0EyScetPJquRFRKIesyJuBFMAs= 8 -----END CERTIFICATE-----
ADDITIONAL_CA_CERT_BUNDLE 的值也可以在 UI 中作为自定义变量进行配置,既可以作为 file,这需要证书的路径,也可以作为变量,这需要证书的文本表示。
漏洞允许列表
- Tier: Ultimate
- Offering: JihuLab.com, 极狐GitLab 私有化部署, 极狐GitLab 专属
要允许特定漏洞,请按照以下步骤操作:
- 在您的 .gitlab-ci.yml 文件中通过在覆盖容器扫描模板中遵循说明设置 GIT_STRATEGY: fetch。
- 在名为 vulnerability-allowlist.yml 的 YAML 文件中定义允许的漏洞。必须使用 vulnerability-allowlist.yml 数据格式中描述的格式。
- 将 vulnerability-allowlist.yml 文件添加到项目 Git 存储库的根文件夹中。
vulnerability-allowlist.yml 数据格式
vulnerability-allowlist.yml 文件是一个 YAML 文件,指定了 允许 存在的漏洞的 CVE ID 列表,因为它们是 误报 或 不适用。
如果在 vulnerability-allowlist.yml 文件中找到匹配项,则发生以下情况:
- 当分析器生成 gl-container-scanning-report.json 文件时,漏洞 不包括在内。
- 流水线的安全选项卡 不显示 漏洞。它不包括在 JSON 文件中,该文件是安全选项卡的事实来源。
示例 vulnerability-allowlist.yml 文件:
yaml1generalallowlist: 2 CVE-2019-8696: 3 CVE-2014-8166: cups 4 CVE-2017-18248: 5images: 6 registry.gitlab.com/gitlab-org/security-products/dast/webgoat-8.0@sha256: 7 CVE-2018-4180: 8 your.private.registry:5000/centos: 9 CVE-2015-1419: libxml2 10 CVE-2015-1447:
此示例排除 gl-container-scanning-report.json 中的:
- 所有 CVE ID 为 CVE-2019-8696、CVE-2014-8166、CVE-2017-18248 的漏洞。
- 在 registry.gitlab.com/gitlab-org/security-products/dast/webgoat-8.0@sha256 容器镜像中发现的所有 CVE ID 为 CVE-2018-4180 的漏洞。
- 在 your.private.registry:5000/centos 容器中发现的所有 CVE ID 为 CVE-2015-1419、CVE-2015-1447 的漏洞。
文件格式
-
generalallowlist 块允许您全局指定 CVE ID。所有具有匹配 CVE ID 的漏洞将从扫描报告中排除。
-
images 块允许您为每个容器镜像单独指定 CVE ID。所有来自给定镜像的漏洞,匹配的 CVE ID 将从扫描报告中排除。镜像名称是从用于指定要扫描的 Docker 镜像的环境变量之一中检索的,例如 $CI_APPLICATION_REPOSITORY:$CI_APPLICATION_TAG 或 CS_IMAGE。此块中的镜像 必须 与此值匹配并且 不能 包括标签值。例如,如果您使用 CS_IMAGE=alpine:3.7 指定要扫描的镜像,则您将在 images 块中使用 alpine,但不能使用 alpine:3.7。
您可以多种方式指定容器镜像:
- 仅作为镜像名称(例如 centos)。
- 作为完整镜像名称,包括镜像仓库主机名(例如 your.private.registry:5000/centos)。
- 作为完整镜像名称,包括镜像仓库主机名和 sha256 标签(例如 registry.gitlab.com/gitlab-org/security-products/dast/webgoat-8.0@sha256)。
在 CVE ID 后的字符串(例如 cups 和 libxml2)是一个可选评论格式。它对漏洞处理 没有影响。您可以包含评论来描述漏洞。
容器扫描作业日志格式
您可以通过查看 container_scanning 作业详细信息中的容器扫描分析器生成的日志来验证扫描结果和 vulnerability-allowlist.yml 文件的正确性。
日志包含发现的漏洞列表作为表,例如:
plaintext1+------------+-------------------------+------------------------+-----------------------+------------------------------------------------------------------------+ 2| STATUS | CVE SEVERITY | PACKAGE NAME | PACKAGE VERSION | CVE DESCRIPTION | 3+------------+-------------------------+------------------------+-----------------------+------------------------------------------------------------------------+ 4| Approved | High CVE-2019-3462 | apt | 1.4.8 | Incorrect sanitation of the 302 redirect field in HTTP transport metho | 5| | | | | d of apt versions 1.4.8 and earlier can lead to content injection by a | 6| | | | | MITM attacker, potentially leading to remote code execution on the ta | 7| | | | | rget machine. | 8+------------+-------------------------+------------------------+-----------------------+------------------------------------------------------------------------+ 9| Unapproved | Medium CVE-2020-27350 | apt | 1.4.8 | APT had several integer overflows and underflows while parsing .deb pa | 10| | | | | ckages, aka GHSL-2020-168 GHSL-2020-169, in files apt-pkg/contrib/extr | 11| | | | | acttar.cc, apt-pkg/deb/debfile.cc, and apt-pkg/contrib/arfile.cc. This | 12| | | | | issue affects: apt 1.2.32ubuntu0 versions prior to 1.2.32ubuntu0.2; 1 | 13| | | | | .6.12ubuntu0 versions prior to 1.6.12ubuntu0.2; 2.0.2ubuntu0 versions | 14| | | | | prior to 2.0.2ubuntu0.2; 2.1.10ubuntu0 versions prior to 2.1.10ubuntu0 | 15| | | | | .1; | 16+------------+-------------------------+------------------------+-----------------------+------------------------------------------------------------------------+ 17| Unapproved | Medium CVE-2020-3810 | apt | 1.4.8 | Missing input validation in the ar/tar implementations of APT before v | 18| | | | | ersion 2.1.2 could result in denial of service when processing special | 19| | | | | ly crafted deb files. | 20+------------+-------------------------+------------------------+-----------------------+------------------------------------------------------------------------+
日志中的漏洞在 vulnerability-allowlist.yml 文件中添加了相应的 CVE ID 时标记为 Approved。
在离线环境中运行容器扫描
- Tier: Free, Premium, Ultimate
- Offering: 极狐GitLab 私有化部署
对于有限、受限或间歇性访问外部资源的环境中的实例,需要对容器扫描作业进行一些调整以成功运行。有关更多信息,请参见离线环境。
离线环境的容器扫描要求
要在离线环境中使用容器扫描,您需要:
- 极狐GitLab Runner,使用 docker 或 kubernetes 执行器。
- 配置一个本地 Docker 容器镜像仓库,其中包含容器扫描镜像的副本。您可以在各自的镜像仓库中找到这些镜像:
极狐GitLab 分析器 | 容器镜像仓库 |
---|---|
Container-Scanning | Container-Scanning 容器镜像仓库 |
极狐GitLab Runner 有一个默认 pull policy 为 always,意味着 runner 尝试从极狐GitLab 容器镜像仓库中拉取 Docker 镜像,即使本地副本可用。在离线环境中,极狐GitLab Runner pull_policy 可以设置为 if-not-present,如果您更喜欢使用仅可用的本地 Docker 镜像。然而,我们建议在非离线环境中保持拉取策略设置为 always,因为这可以使您的 CI/CD 流水线使用更新的扫描仪。
Trivy 的自定义证书授权支持
Trivy 的自定义证书授权支持在版本 4.0.0 中引入。
使极狐GitLab 容器扫描分析器镜像在您的 Docker 镜像仓库中可用
对于容器扫描,将以下镜像从 registry.gitlab.com 导入到您的本地 Docker 容器镜像仓库:
plaintextregistry.gitlab.com/security-products/container-scanning:7 registry.gitlab.com/security-products/container-scanning/trivy:7
将 Docker 镜像导入到本地离线 Docker 镜像仓库的过程取决于 您的网络安全策略。请咨询您的 IT 团队,找到一种可以导入或临时访问外部资源的接受和批准的过程。这些扫描仪是定期更新的,您可能能够偶尔自行更新。
有关更多信息,请参见如何使用流水线更新镜像的具体步骤。
有关将 Docker 镜像作为文件保存和传输的详细信息,请参阅 Docker 文档中的 docker save、docker load、docker export 和 docker import。
设置容器扫描 CI/CD 变量以使用本地容器扫描分析器
-
在 .gitlab-ci.yml 文件中覆盖容器扫描模板,以引用在您的本地 Docker 容器镜像仓库中托管的 Docker 镜像:
yamlinclude: - template: Jobs/Container-Scanning.gitlab-ci.yml container_scanning: image: $CI_REGISTRY/namespace/container-scanning
-
如果您的本地 Docker 容器镜像仓库通过 HTTPS 安全运行,但使用的是自签名证书,则必须在上述 .gitlab-ci.yml 文件的 container_scanning 部分中设置 CS_DOCKER_INSECURE: "true"。
使用流水线自动化容器扫描漏洞数据库更新
我们建议您设置一个定时流水线来在预定的时间表上获取最新的漏洞数据库。通过流水线自动化这一过程意味着您不必每次手动完成。您可以使用以下 .gitlab-ci.yml 示例作为模板。
yaml1variables: 2 SOURCE_IMAGE: registry.gitlab.com/security-products/container-scanning:7 3 TARGET_IMAGE: $CI_REGISTRY/namespace/container-scanning 4 5image: docker:latest 6 7update-scanner-image: 8 services: 9 - docker:dind 10 script: 11 - docker pull $SOURCE_IMAGE 12 - docker tag $SOURCE_IMAGE $TARGET_IMAGE 13 - echo "$CI_REGISTRY_PASSWORD" | docker login $CI_REGISTRY --username $CI_REGISTRY_USER --password-stdin 14 - docker push $TARGET_IMAGE
上面的模板适用于在本地安装运行的极狐GitLab Docker 镜像仓库。但是,如果您使用的是非极狐GitLab Docker 镜像仓库,则必须更改 $CI_REGISTRY 值和 docker login 凭据以匹配您本地镜像仓库的详细信息。
扫描外部私有镜像仓库中的镜像
要扫描外部私有镜像仓库中的镜像,您必须配置访问凭据,以便容器扫描分析器在尝试访问要扫描的镜像之前进行身份验证。
如果您使用极狐GitLab 容器镜像仓库,则 CS_REGISTRY_USER 和 CS_REGISTRY_PASSWORD 配置变量会自动设置,您可以跳过此配置。
此示例显示了扫描私有 Google Container Registry 中镜像所需的配置:
yaml1include: 2 - template: Jobs/Container-Scanning.gitlab-ci.yml 3 4container_scanning: 5 variables: 6 CS_REGISTRY_USER: _json_key 7 CS_REGISTRY_PASSWORD: "$GCP_CREDENTIALS" 8 CS_IMAGE: "gcr.io/path-to-you-registry/image:tag"
在提交此配置之前,添加一个 CI/CD 变量为 GCP_CREDENTIALS 包含 JSON 密钥。此外:
- 变量的值可能不符合 隐藏变量 选项的屏蔽要求,因此可能会在作业日志中暴露。
- 如果选择了 项目变量 选项,则扫描可能不会在未保护的功能分支中运行。
- 考虑创建具有只读权限的凭据,并定期轮换它们,如果未选择选项。
启用 FIPS 模式时不支持扫描外部私有镜像仓库中的镜像。
创建和使用 Trivy Java 数据库镜像
使用 trivy 扫描仪时,扫描的容器镜像中发现 jar 文件时,trivy 会下载一个额外的 trivy-java-db 漏洞数据库。默认情况下,trivy-java-db 数据库作为 OCI artifact 托管在 ghcr.io/aquasecurity/trivy-java-db:1。如果此镜像仓库不可访问或响应 TOOMANYREQUESTS,一种解决方案是将 trivy-java-db 镜像到一个更易访问的容器镜像仓库:
yaml1mirror trivy java db: 2 image: 3 name: ghcr.io/oras-project/oras:v1.1.0 4 entrypoint: [""] 5 script: 6 - oras login -u $CI_REGISTRY_USER -p $CI_REGISTRY_PASSWORD $CI_REGISTRY 7 - oras pull ghcr.io/aquasecurity/trivy-java-db:1 8 - oras push $CI_REGISTRY_IMAGE:1 --config /dev/null:application/vnd.aquasec.trivy.config.v1+json javadb.tar.gz:application/vnd.aquasec.trivy.javadb.layer.v1.tar+gzip
漏洞数据库不是常规 Docker 镜像,因此无法使用 docker pull 拉取。转到极狐GitLab UI 中的镜像时会显示一个错误。
如果上述容器镜像仓库为 gitlab.example.com/trivy-java-db-mirror,则容器扫描作业应按以下方式配置。不要在结尾处添加标签 :1,它由 trivy 添加:
yaml1include: 2 - template: Jobs/Container-Scanning.gitlab-ci.yml 3 4container_scanning: 5 variables: 6 CS_TRIVY_JAVA_DB: gitlab.example.com/trivy-java-db-mirror
运行独立的容器扫描工具
可以运行极狐GitLab 容器扫描工具,无需在 CI 作业的上下文中运行即可对 Docker 容器进行扫描。要直接扫描镜像,请按照以下步骤操作:
-
运行 Docker Desktop 或 Docker Machine。
-
运行分析器的 Docker 镜像,在 CI_APPLICATION_REPOSITORY 和 CI_APPLICATION_TAG 变量中传递要分析的镜像和标签:
shell1docker run \ 2 --interactive --rm \ 3 --volume "$PWD":/tmp/app \ 4 -e CI_PROJECT_DIR=/tmp/app \ 5 -e CI_APPLICATION_REPOSITORY=registry.gitlab.com/gitlab-org/security-products/dast/webgoat-8.0@sha256 \ 6 -e CI_APPLICATION_TAG=bc09fe2e0721dfaeee79364115aeedf2174cce0947b9ae5fe7c33312ee019a4e \ 7 registry.gitlab.com/security-products/container-scanning
结果存储在 gl-container-scanning-report.json 中。
报告 JSON 格式
容器扫描工具会生成 JSON 报告,这些报告通过 CI 配置文件中的 artifacts:reports 关键字被极狐GitLab Runner 识别。
一旦 CI 作业完成,Runner 会将这些报告上传到极狐GitLab,然后在 CI 作业产物中可以查看这些报告。在极狐GitLab旗舰版中,这些报告可以在对应的 流水线 中查看,并成为 漏洞报告 的一部分。
这些报告必须遵循 安全报告架构中定义的格式。
有关更多信息,请参阅 安全扫描仪集成。
CycloneDX 软件材料清单
History
- 在极狐GitLab 15.11 中引入。
除了 JSON 报告文件,容器扫描工具还输出一个 CycloneDX 软件材料清单 (SBOM) 用于扫描的镜像。这个 CycloneDX SBOM 命名为 gl-sbom-report.cdx.json,并与 JSON 报告文件保存在同一目录中。此功能仅在使用 Trivy 分析器时支持。
可以在 依赖列表 中查看此报告。
可以与其他作业产物一样下载 CycloneDX SBOM。
容器注册表的容器扫描
- 层级:旗舰版
- 提供:JihuLab.com,私有化部署
History
- 引入于极狐GitLab 17.1,使用名为 enable_container_scanning_for_registry 的功能标志。默认禁用。
- 在极狐GitLab 17.2 中,为私有化部署启用。
- 在极狐GitLab 17.2 中 GA。功能标志 enable_container_scanning_for_registry 已删除。
当容器镜像使用 latest 标签推送时,安全策略机器人会自动触发一个新的流水线中的容器扫描作业,针对默认分支进行扫描。
与常规容器扫描不同,扫描结果不包括安全报告。相反,容器注册表的容器扫描依赖于 持续漏洞扫描 来检查扫描检测的组件。
当识别出安全发现时,极狐GitLab 会用这些发现填充 漏洞报告。漏洞可以在漏洞报告页面的 容器注册表漏洞 标签下查看。
只有当新的咨询发布到 极狐GitLab咨询数据库 时,容器注册表的容器扫描才会填充漏洞报告。
前提条件
- 您必须在项目中至少拥有维护者角色才能启用容器注册表的容器扫描。
- 使用的项目不能为空。如果您仅使用空项目来存储容器镜像,则该功能将无法正常工作。作为解决方法,请确保项目在默认分支上包含初始提交。
- 默认情况下,每个项目每天限制 50 次扫描。
- 您必须配置容器注册表通知。
启用容器注册表的容器扫描
要启用极狐GitLab容器注册表的容器扫描:
- 在左侧边栏,选择 搜索或转到 并找到您的项目。
- 选择 安全 > 安全配置。
- 向下滚动到 容器注册表的容器扫描 部分并打开开关。
漏洞数据库
所有分析器镜像每天都会更新。
这些镜像使用来自上游咨询数据库的数据:
- AlmaLinux 安全咨询
- Amazon Linux 安全中心
- Arch Linux 安全跟踪器
- SUSE CVRF
- CWE 咨询
- Debian 安全漏洞跟踪器
- GitHub 安全咨询
- Go 漏洞数据库
- CBL-Mariner 漏洞数据
- NVD
- OSV
- Red Hat OVAL v2
- Red Hat 安全数据 API
- Photon 安全咨询
- Rocky Linux 更新信息
- Ubuntu CVE 跟踪器(仅来自 2021 年中期及之后的数据源)
在极狐GitLab旗舰版层级中,来自极狐GitLab咨询数据库的数据被合并,以增强来自外部来源的数据。在极狐GitLab专业版和基础版层级中,来自 极狐GitLab咨询数据库(开源版) 的数据被合并,以增强来自外部来源的数据。目前这种增强仅适用于 Trivy 扫描仪的分析器镜像。
其他分析器的数据库更新信息可在维护表中找到。
漏洞解决方案(自动修复)
- 层级:旗舰版
- 提供:JihuLab.com,极狐GitLab私有化部署,极狐GitLab专用
一些漏洞可以通过应用极狐GitLab自动生成的解决方案进行修复。
要启用修复支持,扫描工具 必须 访问由 CS_DOCKERFILE_PATH CI/CD 变量指定的 Dockerfile。要确保扫描工具可以访问此文件,需要在 .gitlab-ci.yml 文件中设置 GIT_STRATEGY: fetch,并按照本文档中描述的覆盖容器扫描模板 部分的说明进行操作。
阅读有关漏洞解决方案的更多信息。
故障排除
docker: Error response from daemon: failed to copy xattrs
当 runner 使用 docker 执行器并且使用 NFS(例如,/var/lib/docker 在 NFS 挂载上)时,容器扫描可能会失败,并出现如下错误:
plaintextdocker: Error response from daemon: failed to copy xattrs: failed to set xattr "security.selinux" on /path/to/file: operation not supported.
这是 Docker 中一个现已修复的错误导致的。为了防止错误,请确保 runner 使用的 Docker 版本为 18.09.03 或更高版本。
获取警告信息 gl-container-scanning-report.json: no matching files
有关此问题的信息,请参阅 一般应用程序安全故障排除部分。
扫描来自 AWS ECR 的镜像时 unexpected status code 401 Unauthorized: Not Authorized
这可能发生在未配置 AWS 区域并且扫描仪无法检索授权令牌时。当您将 SECURE_LOG_LEVEL 设置为 debug 时,会看到如下日志信息:
shell[35mDEBUG[0m failed to get authorization token: MissingRegion: could not find region configuration
要解决此问题,请将 AWS_DEFAULT_REGION 添加到您的 CI/CD 变量中:
yamlvariables: AWS_DEFAULT_REGION: <AWS_REGION_FOR_ECR>
unable to open a file: open /home/gitlab/.cache/trivy/ee/db/metadata.json: no such file or directory
压缩的 Trivy 数据库存储在容器的 /tmp 文件夹中,并在运行时解压到 /home/gitlab/.cache/trivy/{ee|ce}/db。如果您的 runner 配置中有 /tmp 目录的卷挂载,则可能会发生此错误。
要解决此问题,请绑定 /tmp 文件夹中的特定文件或文件夹(例如 /tmp/myfile.txt),而不是绑定整个 /tmp 文件夹。
解决 context deadline exceeded 错误
此错误表示发生了超时。为了解决此问题,请向 container_scanning 作业添加 TRIVY_TIMEOUT 环境变量,并设置一个足够长的持续时间。