mcpField
S
sbom-supply-chain

sbom-supply-chain

github.com/bagelhole安全1.2k328 次安装23 周前更新
代码仓库

关于 sbom-supply-chain

sbom-supply-chain 是面向软件构建与发布团队的技能,涵盖 SBOM 生成、漏洞检查和制品验证。它还介绍制品签名与证明,以及供应链策略执行。

主要功能

  1. 01生成 CycloneDX 和 SPDX SBOM
  2. 02根据 SBOM 匹配漏洞
  3. 03使用 cosign 签署制品
  4. 04附加 SBOM 和来源证明
  5. 05执行验证策略

适用场景

  1. 01为镜像和应用构建生成 SBOM
  2. 02部署前检查依赖项
  3. 03要求制品签名和来源证明
  4. 04准备安全审查及 SLSA 要求

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/bagelhole/devops-security-agent-skills --skill sbom-supply-chain

安装后在 Claude Code 中输入/sbom-supply-chain确认已加载。

详细介绍

SBOM 与供应链安全

通过可复现的元数据和验证门禁提升发布可信度。

何时使用此技能

在以下情况下使用此技能:

  • 为容器镜像或应用构建生成 SBOM
  • 部署前验证依赖项
  • 强制执行签名制品和来源证明策略
  • 准备 SOC2、ISO 27001 或客户安全审查
  • 实施 SLSA 框架要求
  • 响应供应链漏洞(例如 Log4Shell 事件)

前置条件

  • 已安装 syft,用于生成 SBOM
  • 已安装 cdxgen,用于生成 CycloneDX SBOM
  • 使用 grype 对照 SBOM 匹配漏洞
  • 使用 cosign v2+ 进行签名和证明
  • 支持 OCI 制品的容器镜像仓库
  • 具有 OIDC 身份、用于无密钥签名的 CI/CD 流水线

SBOM 格式

CycloneDX 与 SPDX 对比
comparison:
  cyclonedx:
    standard: "OWASP CycloneDX"
    focus: "Application security, vulnerability tracking"
    formats: ["JSON", "XML", "Protocol Buffers"]
    strengths:
      - Vulnerability references (VEX support)
      - Service and API dependency tracking
      - Hardware BOM support
    best_for: "Security-focused SBOM, vulnerability management"

  spdx:
    standard: "Linux Foundation SPDX (ISO/IEC 5962:2021)"
    focus: "License compliance, legal review"
    formats: ["JSON", "RDF/XML", "Tag-Value", "YAML"]
    strengths:
      - ISO standard
      - License expression language
      - Relationship modeling
    best_for: "License compliance, regulatory requirements"

使用 Syft 生成 SBOM

# Generate SBOM for a container image (CycloneDX JSON)
syft ghcr.io/acme/api:v1.2.3 -o cyclonedx-json > sbom-cyclonedx.json

# Generate SBOM in SPDX format
syft ghcr.io/acme/api:v1.2.3 -o spdx-json > sbom-spdx.json

# Generate SBOM from a local directory (source code)
syft dir:. -o cyclonedx-json > sbom-source.json

# Generate SBOM from a Dockerfile/built image
syft docker:my-local-image:latest -o cyclonedx-json > sbom-local.json

# Generate SBOM for a specific package ecosystem
syft dir:. --catalogers python -o cyclonedx-json > sbom-python.json

# Include file hashes for deeper analysis
syft ghcr.io/acme/api:v1.2.3 -o cyclonedx-json --file-metadata > sbom-with-hashes.json

# Multiple output formats simultaneously
syft ghcr.io/acme/api:v1.2.3 \
  -o cyclonedx-json=sbom-cdx.json \
  -o spdx-json=sbom-spdx.json \
  -o table=sbom-summary.txt

使用 cdxgen 生成 SBOM

# Install cdxgen
npm install -g @cyclonedx/cdxgen

# Generate CycloneDX SBOM for a project directory
cdxgen -o sbom.json .

# Specify project type
cdxgen -t python -o sbom-python.json .
cdxgen -t java -o sbom-java.json .
cdxgen -t node -o sbom-node.json .
cdxgen -t go -o sbom-go.json .

# Generate SBOM with evidence (call stacks, file occurrences)
cdxgen --evidence -o sbom-with-evidence.json .

# Generate for a container image
cdxgen -t docker -o sbom-container.json ghcr.io/acme/api:v1.2.3

# Generate with deep analysis (slower but more accurate)
cdxgen --deep -o sbom-deep.json .

# Output in different formats
cdxgen -o sbom.xml --format xml .

漏洞匹配

# Scan SBOM for vulnerabilities with Grype
grype sbom:sbom-cyclonedx.json

# Fail on critical/high vulnerabilities
grype sbom:sbom-cyclonedx.json --fail-on high

# Output as JSON for CI processing
grype sbom:sbom-cyclonedx.json -o json > vulnerability-report.json

# Scan container image directly
grype ghcr.io/acme/api:v1.2.3

# Use Trivy with SBOM input
trivy sbom sbom-cyclonedx.json

# Trivy scan with severity filter
trivy sbom sbom-cyclonedx.json --severity CRITICAL,HIGH --exit-code 1

Cosign 签名和证明

镜像签名
# Keyless signing (recommended - uses OIDC identity from CI)
cosign sign ghcr.io/acme/api@sha256:abc123...

# Sign with a key pair
cosign generate-key-pair
cosign sign --key cosign.key ghcr.io/acme/api@sha256:abc123...

# Verify keyless signature
cosign verify \
  --certificate-identity=https://github.com/acme/api/.github/workflows/build.yml@refs/heads/main \
  --certificate-oidc-issuer=https://token.actions.githubusercontent.com \
  ghcr.io/acme/api@sha256:abc123...

# Verify with key
cosign verify --key cosign.pub ghcr.io/acme/api@sha256:abc123...
SBOM 证明
# Attach SBOM as an in-toto attestation to a container image
cosign attest --predicate sbom-cyclonedx.json \
  --type cyclonedx \
  ghcr.io/acme/api@sha256:abc123...

# Attach SPDX SBOM
cosign attest --predicate sbom-spdx.json \
  --type spdx \
  ghcr.io/acme/api@sha256:abc123...

# Verify SBOM attestation
cosign verify-attestation \
  --type cyclonedx \
  --certificate-identity=https://github.com/acme/api/.github/workflows/build.yml@refs/heads/main \
  --certificate-oidc-issuer=https://token.actions.githubusercontent.com \
  ghcr.io/acme/api@sha256:abc123...

# Extract the SBOM from attestation
cosign verify-attestation --type cyclonedx \
  --certificate-identity=... --certificate-oidc-issuer=... \
  ghcr.io/acme/api@sha256:abc123... | jq -r '.payload' | base64 -d | jq '.predicate'
In-toto 来源证明
# Create a custom provenance attestation
cat > provenance.json << 'EOF'
{
  "buildType": "https://github.com/acme/build-system@v1",
  "builder": {
    "id": "https://github.com/acme/api/.github/workflows/build.yml@refs/heads/main"
  },
  "invocation": {
    "configSource": {
      "uri": "git+https://github.com/acme/api@refs/heads/main",
      "digest": { "sha1": "abc123def456" },
      "entryPoint": ".github/workflows/build.yml"
    }
  },
  "metadata": {
    "buildStartedOn": "2025-01-15T10:00:00Z",
    "buildFinishedOn": "2025-01-15T10:05:00Z",
    "completeness": {
      "parameters": true,
      "environment": true,
      "materials": true
    }
  },
  "materials": [
    {
      "uri": "git+https://github.com/acme/api@refs/heads/main",
      "digest": { "sha1": "abc123def456" }
    },
    {
      "uri": "pkg:docker/[email protected]",
      "digest": { "sha256": "def456..." }
    }
  ]
}
EOF

# Attach provenance attestation
cosign attest --predicate provenance.json \
  --type slsaprovenance \
  ghcr.io/acme/api@sha256:abc123...

CI/CD 流水线集成

# .github/workflows/sbom-supply-chain.yml
name: Build with SBOM and Signing
on:
  push:
    tags: ['v*']

permissions:
  contents: read
  packages: write
  id-token: write  # Required for keyless signing

jobs:
  build-sign-attest:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4

      - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v3

      - name: Login to GHCR
        uses: docker/login-action@v3
        with:
          registry: ghcr.io
          username: ${{ github.actor }}
          password: ${{ secrets.GITHUB_TOKEN }}

      - name: Build and push image
        id: build
        uses: docker/build-push-action@v5
        with:
          push: true
          tags: ghcr.io/${{ github.repository }}:${{ github.ref_name }}

      - name: Install tools
        run: |
          curl -sSfL https://raw.githubusercontent.com/anchore/syft/main/install.sh | sh -s -- -b /usr/local/bin
          curl -sSfL https://raw.githubusercontent.com/anchore/grype/main/install.sh | sh -s -- -b /usr/local/bin

      - name: Generate SBOM
        run: |
          syft ghcr.io/${{ github.repository }}@${{ steps.build.outputs.digest }} \
            -o cyclonedx-json=sbom-cdx.json \
            -o spdx-json=sbom-spdx.json

      - name: Scan SBOM for vulnerabilities
        run: |
          grype sbom:sbom-cdx.json --fail-on critical -o json > vuln-report.json

      - name: Install cosign
        uses: sigstore/cosign-installer@v3

      - name: Sign image (keyless)
        run: |
          cosign sign ghcr.io/${{ github.repository }}@${{ steps.build.outputs.digest }}

      - name: Attach SBOM attestation
        run: |
          cosign attest --predicate sbom-cdx.json \
            --type cyclonedx \
            ghcr.io/${{ github.repository }}@${{ steps.build.outputs.digest }}

      - name: Upload artifacts
        uses: actions/upload-artifact@v4
        with:
          name: sbom-and-reports
          path: |
            sbom-cdx.json
            sbom-spdx.json
            vuln-report.json

策略执行

Kyverno 策略:要求镜像已签名且包含 SBOM
apiVersion: kyverno.io/v1
kind: ClusterPolicy
metadata:
  name: require-signed-images-with-sbom
spec:
  validationFailureAction: Enforce
  webhookTimeoutSeconds: 30
  rules:
    - name: verify-signature
      match:
        any:
          - resources:
              kinds: ["Pod"]
      verifyImages:
        - imageReferences: ["ghcr.io/acme/*"]
          attestors:
            - entries:
                - keyless:
                    subject: "https://github.com/acme/*"
                    issuer: "https://token.actions.githubusercontent.com"
                    rekor:
                      url: "https://rekor.sigstore.dev"
          attestations:
            - type: cyclonedx
              conditions:
                - all:
                    - key: "{{ components[].name }}"
                      operator: AllNotIn
                      value: ["log4j-core"]
OPA 策略:部署前验证 SBOM
package sbom.verify

import rego.v1

default allow := false

allow if {
    sbom_present
    no_critical_vulns
    signed_by_ci
}

sbom_present if {
    input.attestations.cyclonedx != null
    count(input.attestations.cyclonedx.components) > 0
}

no_critical_vulns if {
    not any_critical
}

any_critical if {
    some vuln in input.vulnerability_report.matches
    vuln.vulnerability.severity == "Critical"
    vuln.vulnerability.fix.state == "fixed"
}

signed_by_ci if {
    input.signature.issuer == "https://token.actions.githubusercontent.com"
    startswith(input.signature.subject, "https://github.com/acme/")
}

故障排除

问题原因解决方案
Syft 遗漏依赖项不支持的包管理器或格式查看 syft catalogers 列表;使用 cdxgen 进行更深入的分析;向上游项目贡献
Cosign 签名失败,提示“no identity token”CI 中缺少 OIDC 提供方确保 GitHub Actions 中具有 id-token: write 权限;检查 OIDC 提供方配置
Grype 报告误报包版本检测不正确验证 SBOM 准确性;向 grype GitHub 仓库报告;为已确认的误报添加忽略规则
SBOM 证明过大镜像较大且依赖项众多压缩 SBOM;使用 SPDX 紧凑格式;考虑按层拆分
准入控制器中的验证失败身份或颁发者 URL 错误检查 --certificate-identity 和 --certificate-oidc-issuer 的准确值
cdxgen 生成的 SBOM 为空未检测到项目类型使用 -t 显式指定类型;确保清单文件(package.json 等)存在

最佳实践

  • 同时生成 CycloneDX 和 SPDX 格式的 SBOM,以实现最大兼容性
  • 使用无密钥签名(Sigstore/Fulcio)为所有发布制品签名
  • 将 SBOM 作为 in-toto 证明附加到容器镜像
  • 在 CI 中扫描 SBOM 中的漏洞,并在发现严重问题时阻止流程
  • 存档每次发布的 SBOM,以用于审计和事件响应
  • 在准入控制器(Kyverno、OPA)中强制执行签名验证
  • 持续监控已存储的 SBOM 中是否出现新的 CVE
  • 在每条构建流水线中加入 SBOM 生成,而不仅限于发布流程
  • 跟踪 SBOM 完整性指标(已捕获依赖项的百分比)
  • 建立 VEX(漏洞可利用性交换)流程来处理误报

相关技能

评论

支持 Markdown