docs consolidation and others
This commit is contained in:
217
docs/modules/attestor/guides/README.md
Normal file
217
docs/modules/attestor/guides/README.md
Normal file
@@ -0,0 +1,217 @@
|
||||
# SBOM Interoperability Testing
|
||||
|
||||
## Overview
|
||||
|
||||
StellaOps SBOM interoperability tests ensure compatibility with third-party security tools in the ecosystem. The tests validate that StellaOps-generated SBOMs can be consumed by popular tools like Grype, and that findings parity remains above 95%.
|
||||
|
||||
## Test Coverage
|
||||
|
||||
### SBOM Formats
|
||||
|
||||
| Format | Version | Status | Parity Target |
|
||||
|--------|---------|--------|---------------|
|
||||
| CycloneDX | 1.6 | ✅ Supported | 95%+ |
|
||||
| SPDX | 3.0.1 | ✅ Supported | 95%+ |
|
||||
|
||||
### Third-Party Tools
|
||||
|
||||
| Tool | Purpose | Version | Status |
|
||||
|------|---------|---------|--------|
|
||||
| Syft | SBOM Generation | Latest | ✅ Compatible |
|
||||
| Grype | Vulnerability Scanning | Latest | ✅ Compatible |
|
||||
| cosign | Attestation | Latest | ✅ Compatible |
|
||||
|
||||
## Parity Expectations
|
||||
|
||||
### What is Parity?
|
||||
|
||||
Parity measures how closely StellaOps vulnerability findings match those from third-party tools like Grype when scanning the same SBOM.
|
||||
|
||||
**Formula:**
|
||||
```
|
||||
Parity % = (Matching Findings / Total Unique Findings) × 100
|
||||
```
|
||||
|
||||
**Target:** ≥95% parity for both CycloneDX and SPDX formats
|
||||
|
||||
### Known Differences
|
||||
|
||||
The following differences are **acceptable** and expected:
|
||||
|
||||
#### 1. VEX Application
|
||||
- **Difference:** StellaOps applies VEX documents, Grype may not
|
||||
- **Impact:** StellaOps may show fewer vulnerabilities
|
||||
- **Acceptable:** Yes - this is a feature, not a bug
|
||||
|
||||
#### 2. Feed Coverage
|
||||
- **Difference:** Tool-specific vulnerability databases
|
||||
- **Examples:**
|
||||
- StellaOps may have distro-specific feeds Grype lacks
|
||||
- Grype may have GitHub Advisory feeds StellaOps doesn't prioritize
|
||||
- **Acceptable:** Within 5% tolerance
|
||||
|
||||
#### 3. Version Matching Semantics
|
||||
- **Difference:** Interpretation of version ranges
|
||||
- **Examples:**
|
||||
- SemVer vs non-SemVer handling
|
||||
- Epoch handling in RPM/Debian packages
|
||||
- **Acceptable:** When using distro-native comparators
|
||||
|
||||
#### 4. Package Identification (PURL)
|
||||
- **Difference:** PURL generation strategies
|
||||
- **Examples:**
|
||||
- `pkg:npm/package` vs `pkg:npm/package@version`
|
||||
- Namespace handling
|
||||
- **Acceptable:** When functionally equivalent
|
||||
|
||||
## Running Interop Tests
|
||||
|
||||
### Prerequisites
|
||||
|
||||
Install required tools:
|
||||
|
||||
```bash
|
||||
# Install Syft
|
||||
curl -sSfL https://raw.githubusercontent.com/anchore/syft/main/install.sh | sh -s -- -b /usr/local/bin
|
||||
|
||||
# Install Grype
|
||||
curl -sSfL https://raw.githubusercontent.com/anchore/grype/main/install.sh | sh -s -- -b /usr/local/bin
|
||||
|
||||
# Install cosign
|
||||
curl -sSfL https://github.com/sigstore/cosign/releases/latest/download/cosign-linux-amd64 -o /usr/local/bin/cosign
|
||||
chmod +x /usr/local/bin/cosign
|
||||
```
|
||||
|
||||
### Local Execution
|
||||
|
||||
```bash
|
||||
# Run all interop tests
|
||||
dotnet test tests/interop/StellaOps.Interop.Tests
|
||||
|
||||
# Run CycloneDX tests only
|
||||
dotnet test tests/interop/StellaOps.Interop.Tests --filter "Format=CycloneDX"
|
||||
|
||||
# Run SPDX tests only
|
||||
dotnet test tests/interop/StellaOps.Interop.Tests --filter "Format=SPDX"
|
||||
|
||||
# Run parity tests
|
||||
dotnet test tests/interop/StellaOps.Interop.Tests --filter "Category=Parity"
|
||||
```
|
||||
|
||||
### CI Execution
|
||||
|
||||
Interop tests run automatically on:
|
||||
- Pull requests affecting scanner or SBOM code
|
||||
- Nightly schedule (6 AM UTC)
|
||||
- Manual workflow dispatch
|
||||
|
||||
See `.gitea/workflows/interop-e2e.yml` for CI configuration.
|
||||
|
||||
## Test Images
|
||||
|
||||
The following container images are used for interop testing:
|
||||
|
||||
| Image | Purpose | Characteristics |
|
||||
|-------|---------|-----------------|
|
||||
| `alpine:3.18` | Distro packages | APK packages, minimal |
|
||||
| `debian:12-slim` | Distro packages | DEB packages, medium |
|
||||
| `ubuntu:22.04` | Distro packages | DEB packages, larger |
|
||||
| `node:20-alpine` | Language packages | NPM packages |
|
||||
| `python:3.12-slim` | Language packages | Pip packages |
|
||||
| `golang:1.22-alpine` | Language packages | Go modules |
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Parity Below Threshold
|
||||
|
||||
If parity drops below 95%:
|
||||
|
||||
1. **Check for feed updates**
|
||||
- Grype may have newer vulnerability data
|
||||
- Update StellaOps feeds
|
||||
|
||||
2. **Review differences**
|
||||
- Run parity analysis: `dotnet test --filter "Category=Parity" --logger "console;verbosity=detailed"`
|
||||
- Categorize differences using `FindingsParityAnalyzer`
|
||||
|
||||
3. **Validate with golden corpus**
|
||||
- Compare against known-good results in `bench/golden-corpus/categories/interop/`
|
||||
|
||||
4. **Update acceptable differences**
|
||||
- Document new acceptable differences in this README
|
||||
- Adjust tolerance if justified
|
||||
|
||||
### Tool Installation Failures
|
||||
|
||||
If Syft/Grype/cosign fail to install:
|
||||
|
||||
```bash
|
||||
# Check versions
|
||||
syft --version
|
||||
grype --version
|
||||
cosign version
|
||||
|
||||
# Reinstall if needed
|
||||
rm /usr/local/bin/{syft,grype,cosign}
|
||||
# Re-run installation commands
|
||||
```
|
||||
|
||||
### SBOM Validation Failures
|
||||
|
||||
If SBOMs fail schema validation:
|
||||
|
||||
1. Verify format version:
|
||||
```bash
|
||||
jq '.specVersion' sbom-cyclonedx.json # Should be "1.6"
|
||||
jq '.spdxVersion' sbom-spdx.json # Should be "SPDX-3.0"
|
||||
```
|
||||
|
||||
2. Validate against official schemas:
|
||||
```bash
|
||||
# CycloneDX
|
||||
npm install -g @cyclonedx/cdx-cli
|
||||
cdx-cli validate --input-file sbom-cyclonedx.json
|
||||
|
||||
# SPDX (TODO: Add SPDX validation tool)
|
||||
```
|
||||
|
||||
## Continuous Improvement
|
||||
|
||||
### Adding New Test Cases
|
||||
|
||||
1. Add new image to test matrix in `*RoundTripTests.cs`
|
||||
2. Update `TestImages` member data
|
||||
3. Run locally to verify
|
||||
4. Submit PR with updated tests
|
||||
|
||||
### Updating Parity Thresholds
|
||||
|
||||
Current threshold: **95%**
|
||||
|
||||
To adjust:
|
||||
1. Document justification in sprint file
|
||||
2. Update `tolerancePercent` parameter in test calls
|
||||
3. Update this README
|
||||
|
||||
### Tool Version Pinning
|
||||
|
||||
Tools are currently installed from `latest`. To pin versions:
|
||||
|
||||
1. Update `.gitea/workflows/interop-e2e.yml`
|
||||
2. Specify version in install commands
|
||||
3. Document version compatibility in this README
|
||||
|
||||
## References
|
||||
|
||||
- [CycloneDX 1.6 Specification](https://cyclonedx.org/docs/1.6/)
|
||||
- [SPDX 3.0.1 Specification](https://spdx.github.io/spdx-spec/v3.0/)
|
||||
- [Syft Documentation](https://github.com/anchore/syft)
|
||||
- [Grype Documentation](https://github.com/anchore/grype)
|
||||
- [cosign Documentation](https://github.com/sigstore/cosign)
|
||||
|
||||
## Contacts
|
||||
|
||||
For questions about interop testing:
|
||||
- **Sprint:** SPRINT_5100_0003_0001
|
||||
- **Owner:** QA Team
|
||||
- **Dependencies:** Sprint 5100.0001.0002 (Evidence Index)
|
||||
630
docs/modules/attestor/guides/cosign-integration.md
Normal file
630
docs/modules/attestor/guides/cosign-integration.md
Normal file
@@ -0,0 +1,630 @@
|
||||
# Cosign Integration Guide
|
||||
|
||||
> **Status:** Ready for Production
|
||||
> **Last Updated:** 2025-12-23
|
||||
> **Prerequisites:** Cosign v2.x, StellaOps CLI v1.5+
|
||||
|
||||
---
|
||||
|
||||
## Overview
|
||||
|
||||
This guide explains how to integrate StellaOps with [Cosign](https://docs.sigstore.dev/cosign/overview/), the signing tool from the Sigstore project. StellaOps can verify and ingest SBOM attestations signed with Cosign, enabling seamless interoperability with the broader supply chain security ecosystem.
|
||||
|
||||
**Key Capabilities:**
|
||||
- ✅ Verify Cosign-signed attestations (SPDX + CycloneDX)
|
||||
- ✅ Extract SBOMs from Cosign DSSE envelopes
|
||||
- ✅ Upload attested SBOMs to StellaOps for scanning
|
||||
- ✅ Offline verification with bundled trust roots
|
||||
- ✅ Custom trust root configuration for air-gapped environments
|
||||
|
||||
---
|
||||
|
||||
## Quick Start
|
||||
|
||||
### 1. Verify a Cosign-Signed Attestation
|
||||
|
||||
```bash
|
||||
# Verify attestation and extract SBOM
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--root /path/to/fulcio-root.pem \
|
||||
--extract-sbom sbom.json
|
||||
|
||||
# Upload extracted SBOM for scanning
|
||||
stella sbom upload \
|
||||
--file sbom.json \
|
||||
--artifact myapp:v1.2.3
|
||||
```
|
||||
|
||||
### 2. End-to-End: Cosign → StellaOps
|
||||
|
||||
```bash
|
||||
# Step 1: Sign SBOM with Cosign
|
||||
cosign attest --predicate sbom.spdx.json \
|
||||
--type spdx \
|
||||
--key cosign.key \
|
||||
myregistry/myapp:v1.2.3
|
||||
|
||||
# Step 2: Fetch attestation
|
||||
cosign verify-attestation myregistry/myapp:v1.2.3 \
|
||||
--key cosign.pub \
|
||||
--type spdx \
|
||||
--output-file attestation.dsse.json
|
||||
|
||||
# Step 3: Verify with StellaOps
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--extract-sbom sbom.spdx.json
|
||||
|
||||
# Step 4: Scan with StellaOps
|
||||
stella scan sbom sbom.spdx.json \
|
||||
--output results.json
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Supported Predicate Types
|
||||
|
||||
StellaOps supports standard SBOM predicate types used by Cosign:
|
||||
|
||||
| Predicate Type | Format | Cosign Flag | StellaOps Support |
|
||||
|----------------|--------|-------------|-------------------|
|
||||
| `https://spdx.dev/Document` | SPDX 3.0.1 | `--type spdx` | ✅ Full support |
|
||||
| `https://spdx.org/spdxdocs/spdx-v2.3-*` | SPDX 2.3 | `--type spdx` | ✅ Full support |
|
||||
| `https://cyclonedx.org/bom` | CycloneDX 1.4-1.7 | `--type cyclonedx` | ✅ Full support |
|
||||
| `https://slsa.dev/provenance/v1` | SLSA v1.0 | `--type slsaprovenance` | ✅ Metadata only |
|
||||
|
||||
---
|
||||
|
||||
## Common Workflows
|
||||
|
||||
### Workflow 1: Keyless Signing (Fulcio)
|
||||
|
||||
**Use Case:** Sign attestations using ephemeral keys from Fulcio (requires OIDC).
|
||||
|
||||
```bash
|
||||
# Step 1: Generate SBOM (using Syft as example)
|
||||
syft myregistry/myapp:v1.2.3 -o spdx-json=sbom.spdx.json
|
||||
|
||||
# Step 2: Sign with Cosign (keyless)
|
||||
cosign attest --predicate sbom.spdx.json \
|
||||
--type spdx \
|
||||
myregistry/myapp:v1.2.3
|
||||
|
||||
# Step 3: Verify with StellaOps (uses Sigstore public instance)
|
||||
stella attest verify-image myregistry/myapp:v1.2.3 \
|
||||
--type spdx \
|
||||
--extract-sbom sbom-verified.spdx.json
|
||||
|
||||
# Step 4: Scan
|
||||
stella scan sbom sbom-verified.spdx.json
|
||||
```
|
||||
|
||||
**Trust Configuration:**
|
||||
StellaOps defaults to the Sigstore public instance trust roots:
|
||||
- Fulcio root: https://fulcio.sigstore.dev/api/v2/trustBundle
|
||||
- Rekor instance: https://rekor.sigstore.dev
|
||||
|
||||
### Workflow 2: Key-Based Signing
|
||||
|
||||
**Use Case:** Sign attestations with your own keys (air-gapped environments).
|
||||
|
||||
```bash
|
||||
# Step 1: Generate key pair (one-time)
|
||||
cosign generate-key-pair
|
||||
|
||||
# Step 2: Sign SBOM
|
||||
cosign attest --predicate sbom.spdx.json \
|
||||
--type spdx \
|
||||
--key cosign.key \
|
||||
myregistry/myapp:v1.2.3
|
||||
|
||||
# Step 3: Export attestation
|
||||
cosign verify-attestation myregistry/myapp:v1.2.3 \
|
||||
--key cosign.pub \
|
||||
--type spdx \
|
||||
--output-file attestation.dsse.json
|
||||
|
||||
# Step 4: Verify with StellaOps (custom public key)
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--public-key cosign.pub \
|
||||
--extract-sbom sbom.spdx.json
|
||||
|
||||
# Step 5: Upload to StellaOps
|
||||
stella sbom upload --file sbom.spdx.json --artifact myapp:v1.2.3
|
||||
```
|
||||
|
||||
### Workflow 3: CycloneDX Attestations
|
||||
|
||||
**Use Case:** Work with CycloneDX BOMs from Trivy.
|
||||
|
||||
```bash
|
||||
# Step 1: Generate CycloneDX SBOM with Trivy
|
||||
trivy image myregistry/myapp:v1.2.3 \
|
||||
--format cyclonedx \
|
||||
--output sbom.cdx.json
|
||||
|
||||
# Step 2: Sign with Cosign
|
||||
cosign attest --predicate sbom.cdx.json \
|
||||
--type cyclonedx \
|
||||
--key cosign.key \
|
||||
myregistry/myapp:v1.2.3
|
||||
|
||||
# Step 3: Fetch and verify
|
||||
cosign verify-attestation myregistry/myapp:v1.2.3 \
|
||||
--key cosign.pub \
|
||||
--type cyclonedx \
|
||||
--output-file attestation.dsse.json
|
||||
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--public-key cosign.pub \
|
||||
--extract-sbom sbom.cdx.json
|
||||
|
||||
# Step 4: Scan
|
||||
stella scan sbom sbom.cdx.json
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## CLI Reference
|
||||
|
||||
### `stella attest verify`
|
||||
|
||||
Verify a Cosign-signed attestation and optionally extract the SBOM.
|
||||
|
||||
```bash
|
||||
stella attest verify [OPTIONS]
|
||||
|
||||
Options:
|
||||
--envelope FILE DSSE envelope file (required)
|
||||
--root FILE Fulcio root certificate (for keyless)
|
||||
--public-key FILE Public key file (for key-based)
|
||||
--extract-sbom FILE Extract SBOM to file
|
||||
--offline Offline verification mode
|
||||
--checkpoint FILE Rekor checkpoint for offline verification
|
||||
--trust-root DIR Directory with trust roots
|
||||
--output FILE Verification report output (JSON)
|
||||
|
||||
Examples:
|
||||
# Keyless verification (Sigstore public instance)
|
||||
stella attest verify --envelope attestation.dsse.json
|
||||
|
||||
# Key-based verification
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--public-key cosign.pub
|
||||
|
||||
# Extract SBOM during verification
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--extract-sbom sbom.json
|
||||
|
||||
# Offline verification
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--offline \
|
||||
--trust-root /opt/stellaops/trust-roots \
|
||||
--checkpoint rekor-checkpoint.json
|
||||
```
|
||||
|
||||
### `stella attest extract-sbom`
|
||||
|
||||
Extract SBOM from a DSSE envelope without verification.
|
||||
|
||||
```bash
|
||||
stella attest extract-sbom [OPTIONS]
|
||||
|
||||
Options:
|
||||
--envelope FILE DSSE envelope file (required)
|
||||
--output FILE Output SBOM file (required)
|
||||
--format FORMAT Force format (spdx|cyclonedx)
|
||||
|
||||
Example:
|
||||
stella attest extract-sbom \
|
||||
--envelope attestation.dsse.json \
|
||||
--output sbom.spdx.json
|
||||
```
|
||||
|
||||
### `stella attest verify-image`
|
||||
|
||||
Verify attestations attached to an OCI image.
|
||||
|
||||
```bash
|
||||
stella attest verify-image IMAGE [OPTIONS]
|
||||
|
||||
Options:
|
||||
--type TYPE Predicate type (spdx|cyclonedx|slsaprovenance)
|
||||
--extract-sbom FILE Extract SBOM to file
|
||||
--public-key FILE Public key (for key-based signing)
|
||||
--offline Offline mode
|
||||
|
||||
Example:
|
||||
stella attest verify-image myregistry/myapp:v1.2.3 \
|
||||
--type spdx \
|
||||
--extract-sbom sbom.spdx.json
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Trust Configuration
|
||||
|
||||
### Default Trust Roots (Public Sigstore)
|
||||
|
||||
StellaOps defaults to the Sigstore public instance:
|
||||
|
||||
```yaml
|
||||
# Default configuration (built-in)
|
||||
attestor:
|
||||
trustRoots:
|
||||
sigstore:
|
||||
enabled: true
|
||||
fulcioRootUrl: https://fulcio.sigstore.dev/api/v2/trustBundle
|
||||
rekorInstanceUrl: https://rekor.sigstore.dev
|
||||
cacheTTL: 24h
|
||||
```
|
||||
|
||||
### Custom Trust Roots (Air-Gapped)
|
||||
|
||||
For air-gapped environments, provide trust roots offline:
|
||||
|
||||
```yaml
|
||||
# /etc/stellaops/attestor.yaml
|
||||
attestor:
|
||||
trustRoots:
|
||||
custom:
|
||||
enabled: true
|
||||
fulcioRoots:
|
||||
- /opt/stellaops/trust-roots/fulcio-root.pem
|
||||
- /opt/stellaops/trust-roots/fulcio-intermediate.pem
|
||||
rekorPublicKeys:
|
||||
- /opt/stellaops/trust-roots/rekor.pub
|
||||
ctfePublicKeys:
|
||||
- /opt/stellaops/trust-roots/ctfe.pub
|
||||
```
|
||||
|
||||
**Trust Root Bundle Structure:**
|
||||
```
|
||||
/opt/stellaops/trust-roots/
|
||||
├── fulcio-root.pem # Fulcio root CA
|
||||
├── fulcio-intermediate.pem # Fulcio intermediate CA (optional)
|
||||
├── rekor.pub # Rekor public key
|
||||
├── ctfe.pub # Certificate Transparency log public key
|
||||
└── checkpoints/ # Cached Rekor checkpoints
|
||||
└── rekor-checkpoint.json
|
||||
```
|
||||
|
||||
### Downloading Trust Roots
|
||||
|
||||
```bash
|
||||
# Download Sigstore public trust bundle
|
||||
curl -o trust-bundle.json \
|
||||
https://tuf.sigstore.dev/targets/trusted_root.json
|
||||
|
||||
# Extract Fulcio roots
|
||||
stella trust extract-fulcio-roots \
|
||||
--bundle trust-bundle.json \
|
||||
--output /opt/stellaops/trust-roots/
|
||||
|
||||
# Extract Rekor public keys
|
||||
stella trust extract-rekor-keys \
|
||||
--bundle trust-bundle.json \
|
||||
--output /opt/stellaops/trust-roots/
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Offline Verification
|
||||
|
||||
### Prerequisites
|
||||
|
||||
1. Trust roots downloaded and extracted
|
||||
2. Rekor checkpoint bundle downloaded
|
||||
3. Attestation DSSE envelope available locally
|
||||
|
||||
### Workflow
|
||||
|
||||
```bash
|
||||
# Step 1: Download trust bundle (online, one-time)
|
||||
stella trust download --output /opt/stellaops/trust-roots/
|
||||
|
||||
# Step 2: Download Rekor checkpoint (online, periodic)
|
||||
stella trust checkpoint download \
|
||||
--output /opt/stellaops/trust-roots/checkpoints/rekor-checkpoint.json
|
||||
|
||||
# Step 3: Verify offline (air-gapped environment)
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--offline \
|
||||
--trust-root /opt/stellaops/trust-roots \
|
||||
--checkpoint /opt/stellaops/trust-roots/checkpoints/rekor-checkpoint.json \
|
||||
--extract-sbom sbom.json
|
||||
|
||||
# Step 4: Scan offline
|
||||
stella scan sbom sbom.json --offline
|
||||
```
|
||||
|
||||
### Checkpoint Freshness
|
||||
|
||||
Rekor checkpoints should be refreshed periodically:
|
||||
- **High Security:** Daily updates
|
||||
- **Standard:** Weekly updates
|
||||
- **Low Risk:** Monthly updates
|
||||
|
||||
Set a reminder to refresh checkpoints:
|
||||
```bash
|
||||
# Cron job (daily at 2 AM)
|
||||
0 2 * * * /usr/local/bin/stella trust checkpoint download --output /opt/stellaops/trust-roots/checkpoints/
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Error: "Unsupported predicate type"
|
||||
|
||||
**Cause:** The DSSE envelope contains a predicate type not supported by StellaOps.
|
||||
|
||||
**Solution:** Check the predicate type:
|
||||
```bash
|
||||
stella attest inspect --envelope attestation.dsse.json
|
||||
|
||||
# Output will show:
|
||||
# Predicate Type: https://example.com/custom-type
|
||||
# Supported: false
|
||||
```
|
||||
|
||||
If the predicate is SPDX or CycloneDX, ensure you're using StellaOps CLI v1.5+.
|
||||
|
||||
### Error: "Signature verification failed"
|
||||
|
||||
**Cause:** The signature cannot be verified against the provided trust roots.
|
||||
|
||||
**Troubleshooting Steps:**
|
||||
1. Check trust root configuration:
|
||||
```bash
|
||||
stella attest verify --envelope attestation.dsse.json --debug
|
||||
```
|
||||
|
||||
2. Verify the public key matches:
|
||||
```bash
|
||||
# Extract public key from certificate in DSSE envelope
|
||||
stella attest inspect --envelope attestation.dsse.json --show-cert
|
||||
|
||||
# Compare with your public key
|
||||
cat cosign.pub
|
||||
```
|
||||
|
||||
3. For keyless signing, ensure Fulcio root is correct:
|
||||
```bash
|
||||
# Test Fulcio connectivity
|
||||
curl -v https://fulcio.sigstore.dev/api/v2/trustBundle
|
||||
```
|
||||
|
||||
### Error: "Failed to extract SBOM"
|
||||
|
||||
**Cause:** The predicate payload is not a valid SBOM.
|
||||
|
||||
**Solution:** Inspect the predicate:
|
||||
```bash
|
||||
stella attest inspect --envelope attestation.dsse.json --show-predicate
|
||||
```
|
||||
|
||||
Check if the predicate type matches the actual content:
|
||||
- `https://spdx.dev/Document` should contain SPDX JSON
|
||||
- `https://cyclonedx.org/bom` should contain CycloneDX JSON
|
||||
|
||||
### Warning: "Checkpoint is stale"
|
||||
|
||||
**Cause:** The Rekor checkpoint is older than the freshness threshold (default: 7 days).
|
||||
|
||||
**Solution:** Download a fresh checkpoint:
|
||||
```bash
|
||||
stella trust checkpoint download \
|
||||
--output /opt/stellaops/trust-roots/checkpoints/rekor-checkpoint.json
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Verify Before Extraction
|
||||
|
||||
Always verify the attestation signature before extracting the SBOM:
|
||||
|
||||
```bash
|
||||
# ✅ GOOD: Verify then extract
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--extract-sbom sbom.json
|
||||
|
||||
# ❌ BAD: Extract without verification
|
||||
stella attest extract-sbom \
|
||||
--envelope attestation.dsse.json \
|
||||
--output sbom.json
|
||||
```
|
||||
|
||||
### 2. Use Keyless Signing for Public Images
|
||||
|
||||
For public container images, use keyless signing (Fulcio):
|
||||
- No key management overhead
|
||||
- Identity verified via OIDC
|
||||
- Transparent via Rekor
|
||||
|
||||
```bash
|
||||
# Keyless signing (recommended for public images)
|
||||
cosign attest --predicate sbom.spdx.json \
|
||||
--type spdx \
|
||||
myregistry/publicapp:v1.0.0
|
||||
```
|
||||
|
||||
### 3. Use Key-Based Signing for Private/Air-Gapped
|
||||
|
||||
For private registries or air-gapped environments, use key-based signing:
|
||||
- Full control over keys
|
||||
- No external dependencies
|
||||
- Works offline
|
||||
|
||||
```bash
|
||||
# Key-based signing (recommended for private/air-gapped)
|
||||
cosign attest --predicate sbom.spdx.json \
|
||||
--type spdx \
|
||||
--key cosign.key \
|
||||
myregistry/privateapp:v1.0.0
|
||||
```
|
||||
|
||||
### 4. Automate Trust Root Updates
|
||||
|
||||
Set up automated trust root updates:
|
||||
|
||||
```bash
|
||||
#!/bin/bash
|
||||
# /usr/local/bin/update-trust-roots.sh
|
||||
|
||||
set -e
|
||||
|
||||
TRUST_DIR=/opt/stellaops/trust-roots
|
||||
|
||||
# Download latest trust bundle
|
||||
stella trust download --output $TRUST_DIR --force
|
||||
|
||||
# Download fresh checkpoint
|
||||
stella trust checkpoint download --output $TRUST_DIR/checkpoints/
|
||||
|
||||
# Verify trust roots
|
||||
stella trust verify --trust-root $TRUST_DIR
|
||||
|
||||
echo "Trust roots updated successfully"
|
||||
```
|
||||
|
||||
### 5. Include Attestation in CI/CD
|
||||
|
||||
Integrate attestation verification into your CI/CD pipeline:
|
||||
|
||||
**GitHub Actions Example:**
|
||||
```yaml
|
||||
name: Verify SBOM Attestation
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
|
||||
jobs:
|
||||
verify:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install StellaOps CLI
|
||||
run: |
|
||||
curl -sSfL https://cli.stellaops.io/install.sh | sh
|
||||
sudo mv stella /usr/local/bin/
|
||||
|
||||
- name: Verify attestation
|
||||
run: |
|
||||
stella attest verify-image \
|
||||
${{ env.IMAGE_REF }} \
|
||||
--type spdx \
|
||||
--extract-sbom sbom.spdx.json
|
||||
|
||||
- name: Scan SBOM
|
||||
run: |
|
||||
stella scan sbom sbom.spdx.json \
|
||||
--policy production \
|
||||
--fail-on blocked
|
||||
|
||||
- name: Upload results
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: scan-results
|
||||
path: sbom.spdx.json
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Advanced Topics
|
||||
|
||||
### Multi-Signature Verification
|
||||
|
||||
Cosign supports multiple signatures on a single attestation. StellaOps verifies all signatures:
|
||||
|
||||
```bash
|
||||
# Attestation with multiple signatures
|
||||
cosign verify-attestation myregistry/myapp:v1.2.3 \
|
||||
--key cosign-key1.pub \
|
||||
--key cosign-key2.pub \
|
||||
--type spdx \
|
||||
--output-file attestation.dsse.json
|
||||
|
||||
# StellaOps verifies all signatures
|
||||
stella attest verify \
|
||||
--envelope attestation.dsse.json \
|
||||
--public-key cosign-key1.pub \
|
||||
--public-key cosign-key2.pub \
|
||||
--require-all-signatures
|
||||
```
|
||||
|
||||
### Custom Predicate Types
|
||||
|
||||
If you have custom predicate types, register them with StellaOps:
|
||||
|
||||
```yaml
|
||||
# /etc/stellaops/attestor.yaml
|
||||
attestor:
|
||||
predicates:
|
||||
custom:
|
||||
- type: https://example.com/custom-sbom@v1
|
||||
parser: custom-sbom-parser
|
||||
schema: /opt/stellaops/schemas/custom-sbom.schema.json
|
||||
```
|
||||
|
||||
### Batch Verification
|
||||
|
||||
Verify multiple attestations in batch:
|
||||
|
||||
```bash
|
||||
# Create batch file
|
||||
cat > batch.txt <<EOF
|
||||
attestation1.dsse.json
|
||||
attestation2.dsse.json
|
||||
attestation3.dsse.json
|
||||
EOF
|
||||
|
||||
# Batch verify
|
||||
stella attest verify-batch \
|
||||
--input batch.txt \
|
||||
--public-key cosign.pub \
|
||||
--output-dir verified-sboms/
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## References
|
||||
|
||||
### External Documentation
|
||||
- [Cosign Documentation](https://docs.sigstore.dev/cosign/overview/)
|
||||
- [Sigstore Trust Root Specification](https://github.com/sigstore/root-signing)
|
||||
- [in-toto Attestation Specification](https://github.com/in-toto/attestation)
|
||||
- [SPDX 3.0.1 Specification](https://spdx.github.io/spdx-spec/v3.0.1/)
|
||||
- [CycloneDX 1.6 Specification](https://cyclonedx.org/docs/1.6/)
|
||||
|
||||
### StellaOps Documentation
|
||||
- [Attestor Architecture](../modules/attestor/architecture.md)
|
||||
- [Standard Predicate Types](../modules/attestor/predicate-parsers.md)
|
||||
- [CLI Reference](../API_CLI_REFERENCE.md)
|
||||
- [Offline Kit Guide](../OFFLINE_KIT.md)
|
||||
|
||||
---
|
||||
|
||||
## Feedback
|
||||
|
||||
Found an issue or have a suggestion? Please report it:
|
||||
- GitHub: https://github.com/stella-ops/stella-ops/issues
|
||||
- Docs: https://docs.stellaops.io/integrations/cosign
|
||||
- Community: https://community.stellaops.io/c/integrations
|
||||
|
||||
---
|
||||
|
||||
**Last Updated:** 2025-12-23
|
||||
**Applies To:** StellaOps CLI v1.5+, Cosign v2.x
|
||||
Reference in New Issue
Block a user