save checkpoint

This commit is contained in:
master
2026-02-11 01:32:14 +02:00
parent 5593212b41
commit cf5b72974f
2316 changed files with 68799 additions and 3808 deletions

View File

@@ -39,6 +39,15 @@ Key settings:
## Related Documentation
- Operations: `./operations/` (if exists)
- Portable pack contract: `./portable-audit-pack-contract.md`
- Portable manifest schema: `./schemas/portable-audit-pack-manifest.v1.schema.json`
- Portable compatibility mapping: `./portable-audit-pack-compatibility.md`
- Portable determinism profile: `./portable-audit-pack-determinism.md`
- Portable Rekor offline profile: `./portable-audit-pack-rekor-offline.md`
- Portable CLI runbook: `./portable-audit-pack-cli-runbook.md`
- Portable Parquet profile: `./portable-audit-pack-parquet-profile.md`
- Portable verification matrix: `./portable-audit-pack-test-matrix.md`
- Promotion evidence contract: `./promotion-evidence-contract.md`
- ExportCenter: `../export-center/`
- Attestor: `../attestor/`
- High-Level Architecture: `../../ARCHITECTURE_OVERVIEW.md`

View File

@@ -276,6 +276,7 @@ Bundle N-1 Bundle N Bundle N+1
* Attestation contract: `./attestation-contract.md`
* Evidence bundle spec: `./evidence-bundle-v1.md`
* Evidence pack schema: `./guides/evidence-pack-schema.md`
* Promotion gate evidence contract: `./promotion-evidence-contract.md`
* Audit bundle index schema: `./schemas/audit-bundle-index.schema.json`
* ExportCenter: `../export-center/architecture.md`
* Attestor: `../attestor/architecture.md`

View File

@@ -93,3 +93,23 @@ Validation is fail-closed:
- reject invalid Rekor index values
This contract is authoritative for Sprint 110 and blocks CONCELIER-ATTEST-73-001/002 and EXCITITOR-ATTEST-01-003/73-001/73-002.
## Gate Artifact Extension (v1.1, 2026-02-10)
Promotion evidence consumers now rely on additional optional fields for policy-gate semantics:
- `producer_bundle.evidence_score_value` (0-100 numeric score for threshold checks)
- `producer_bundle.build_link.exists` (bool)
- `producer_bundle.build_link.product_digest.sha256|sha512` (optional digest binding inputs)
- `producer_bundle.artifact_digest.sha256|sha512` (optional explicit artifact digest)
- `producer_bundle.dsse_signatures[]`:
- `key_id`
- `algorithm`
- `valid`
- `producer_bundle.rekor.checked_at` (UTC RFC3339 timestamp for freshness TTL checks)
- `producer_bundle.human_decision_dsse_ref` (optional DSSE reference for signed escalation disposition)
Offline exports must retain enough metadata for air-gapped gate replay:
- Rekor proof references (`tile_id`, `inclusion_proof_path`) and freshness timestamp.
- DSSE signer evidence needed for k-of-n verification.
- Human decision DSSE reference when escalation policy requires signed disposition.

View File

@@ -0,0 +1,52 @@
# Portable Audit Pack CLI Runbook
Status: Target behavior for implementation sprint handoff (2026-02-10).
## Objective
Define expected parity between generation and verification CLI flows for portable audit packs in connected and air-gapped environments.
## Export workflow (target)
```bash
stella auditpack export \
--artifact myorg/myapp@sha256:<digest> \
--bom sbom.json \
--vex vex/*.json \
--out artifact-audit-pack.tzst \
--profile portable-v1 \
--rekor-tiles fetch \
--sign-key ed25519:stella-bom-signer@2026Q1
```
Expected behavior:
- Emits manifest conforming to `portable-audit-pack-manifest.v1.schema.json`.
- Produces deterministic archive metadata and ordered contents.
- Emits stable machine-readable summary ordered by file path.
## Verify workflow (target)
```bash
stella auditpack verify artifact-audit-pack.tzst --offline --profile portable-v1
```
Required checks:
- Manifest signature verification.
- File digest and size verification.
- DSSE payload digest binding verification.
- Rekor inclusion/root verification from bundled material.
- Optional Parquet fingerprint verification when present.
## Output contract
- Human output grouped in fixed order: manifest -> file digests -> DSSE -> Rekor -> optional index.
- JSON output fields sorted lexicographically for deterministic diffing.
- Non-zero exit and stable error codes on first failure.
## Air-gap operator sequence
1. Transfer bundle to offline verifier host.
2. Run `stella auditpack verify ... --offline`.
3. Archive verification output with audit evidence.
4. Record profile version and verifier key IDs in release record.
## Documentation dependency
- Keep this runbook aligned with:
- `portable-audit-pack-contract.md`
- `portable-audit-pack-rekor-offline.md`
- `portable-audit-pack-test-matrix.md`

View File

@@ -0,0 +1,40 @@
# Portable Audit Pack Compatibility Mapping
Status: Draft frozen for implementation handoff (2026-02-10).
## Purpose
Map current StellaOps evidence bundle contracts to the portable audit pack profile so writer/reader implementations use one required field model.
## Canonical contract source
- Manifest schema: `docs/modules/evidence-locker/schemas/portable-audit-pack-manifest.v1.schema.json`
- Profile contract: `docs/modules/evidence-locker/portable-audit-pack-contract.md`
## Required field mapping
| Portable field | Existing source contract | Notes |
| --- | --- | --- |
| `spec_version` | `bundle.manifest.schema.json` `manifestVersion` | Portable uses fixed `1.0`. |
| `artifact.digest.sha256` | `evidence-bundle-v1.md` subject digest | Required, lowercase hex without `sha256:` prefix in manifest payload fields. |
| `files[*].sha256` | `checksums.schema.json` + bundle manifest entries | Portable stores per-file metadata directly in `files` map. |
| `digests.canonical_bom_sha256` | `stellaops-evidence-pack.v1.schema.json` digest fields | New explicit top-level binding for BOM canonical bytes. |
| `digests.dsse_payload_digest.sha256` | `attestation-contract.md` producer bundle digest linkage | Required preimage binding for DSSE payload verification. |
| `rekor.tile_refs[]` | `attestor/transparency.md` + Rekor receipt inputs | Portable requires deterministic path references under `rekor/`. |
| `rekor.root_hash` | Attestor checkpoint verification contract | Captured at inclusion checkpoint used by offline verifier. |
| `verifiers.pubkeys[]` | Existing key bundle references | Portable manifest contains verifier key references used by CLI/offline verifier. |
## Legacy bundle compatibility
- Legacy `evidence-bundle-<id>.tar.gz` and `portable-bundle-v1.tgz` remain valid for existing tooling.
- Portable audit pack profile is additive and must not reinterpret legacy fields silently.
- Readers should apply this precedence:
1. If `spec_version` exists and equals `1.0`, validate against portable schema.
2. Else if `manifestVersion` exists, validate against legacy `bundle.manifest.schema.json`.
3. Else fail closed with `ERR_MANIFEST_PROFILE_UNKNOWN`.
## Writer/reader alignment rules
- Writers MUST populate every required portable field in schema v1.
- Readers MUST reject packs missing any required portable field.
- Writers/readers MUST share the same portable schema artifact ID and hash in release notes.
## Migration notes
- Maintain both parsers during transition.
- Export paths should emit explicit profile indicator in logs and operator output.
- Verification output should identify which profile was validated.

View File

@@ -0,0 +1,106 @@
# Portable Audit Pack Contract (v1 Draft)
## Purpose
Define a deterministic, offline-verifiable portable audit pack contract that unifies Stella Ops evidence export semantics across Attestor, EvidenceLocker, AuditPack, and CLI verification flows.
## Contract status
- Status: Draft for implementation.
- Source sprint: `docs-archived/implplan/2026-02-10-completed-sprints/SPRINT_20260210_003_DOCS_portable_audit_pack_translation.md`
- Canonical schema: `docs/modules/evidence-locker/schemas/portable-audit-pack-manifest.v1.schema.json`
## Companion profile documents
- Compatibility mapping: `docs/modules/evidence-locker/portable-audit-pack-compatibility.md`
- Determinism profile: `docs/modules/evidence-locker/portable-audit-pack-determinism.md`
- Rekor offline verification profile: `docs/modules/evidence-locker/portable-audit-pack-rekor-offline.md`
- CLI runbook (target behavior): `docs/modules/evidence-locker/portable-audit-pack-cli-runbook.md`
- Optional Parquet profile: `docs/modules/evidence-locker/portable-audit-pack-parquet-profile.md`
- Verification test matrix: `docs/modules/evidence-locker/portable-audit-pack-test-matrix.md`
## Target bundle profile
### Required artifacts
- `manifest.json` (JCS canonical JSON)
- `manifest.sig` (DSSE envelope over canonical manifest, detached file)
- `canonical_bom.json` (canonicalized BOM snapshot)
- `dsse_envelope.json` (attestation envelope bound to BOM/subject)
- `rekor/` proof material:
- checkpoint note/signature
- inclusion proof data
- tile bundle reference material (`tile.tar` or equivalent deterministic bundle)
### Optional artifacts
- `merged_vex.json` (canonical merged VEX view)
- `components.parquet` (optional analytics profile)
- `checksums.txt` / replay helper assets for operational workflows
## Manifest contract (portable profile)
### Core fields
- `spec_version`
- `created_utc`
- `artifact` (`name`, `version`, `digest`, `media_type`)
- `files` map with per-file:
- `sha256`
- `size`
- `content_type`
- profile-specific metadata (for example `compression`, `schema_fingerprint`)
- `digests`:
- `canonical_bom_sha256`
- `dsse_payload_digest`
- `rekor`:
- `log_id`
- `api_version`
- `tile_refs`
- `root_hash`
- `timestamps`
- `verifiers` (key references and trust metadata)
Schema note:
- Required field set and allowed optional fields are frozen in `portable-audit-pack-manifest.v1.schema.json`.
### Determinism rules
- JSON canonicalization MUST use RFC 8785/JCS-compatible canonical output.
- Manifest signing input MUST be the canonical bytes of `manifest.json`.
- File inventory MUST be sorted lexicographically by canonical path.
- Archive metadata MUST be deterministic (mtime, uid/gid, mode, ordering).
- Digests MUST be lowercase SHA-256 hex unless profile explicitly states otherwise.
## Verification contract
1. Verify `manifest.sig` against canonical `manifest.json`.
2. Verify every file digest/size in `manifest.files`.
3. Verify DSSE envelope signature(s) and payload digest binding.
4. Verify Rekor inclusion proof against checkpoint root using bundled proof/tile data.
5. Verify artifact/BOM subject digest consistency.
6. If `components.parquet` is present, validate schema fingerprint metadata.
Default policy is fail-closed for missing or invalid required verification inputs.
## Current state vs target (gap summary)
- Implemented:
- Detached `manifest.sig` support in audit bundle paths.
- Rekor offline proof verification primitives.
- EvidenceLocker fields for canonical BOM/payload digest and Rekor refs.
- Gaps:
- No single unified portable manifest schema with full required field set.
- Non-uniform canonicalization implementations across pack writers.
- Determinism not fully enforced across all packaging flows.
- Optional Parquet profile not defined in portable pack contract.
## Ownership map
- `Attestor`: DSSE/Rekor proof verification contract and tile/checkpoint binding.
- `EvidenceLocker`: persistence/export schema and portable bundle profile publication.
- `StellaOps.AuditPack`: deterministic pack write/read/sign/verify implementation.
- `CLI`: pack generation and offline verification UX parity.
- `QA`: deterministic fixtures, tamper matrix, replay verification.
## Implementation notes
- Keep compatibility mapping for legacy bundle manifests; do not silently reinterpret fields.
- Keep offline posture: no mandatory network calls in verification.
- Prefer shared canonicalization libraries over local ad hoc JSON serializers.
## References
- `docs/modules/attestor/repro-bundle-profile.md`
- `docs/modules/attestor/transparency.md`
- `docs/modules/evidence-locker/export-format.md`
- `docs/modules/evidence-locker/schemas/audit-bundle-index.schema.json`
- `docs/modules/evidence-locker/schemas/stellaops-evidence-pack.v1.schema.json`

View File

@@ -0,0 +1,46 @@
# Portable Audit Pack Determinism Profile
Status: Draft frozen for implementation handoff (2026-02-10).
## Scope
Deterministic requirements for portable pack generation (`manifest.json`, BOM, DSSE envelope, Rekor material, optional VEX/Parquet artifacts).
## Normative rules
1. Canonical JSON MUST use RFC 8785/JCS-compatible serialization.
2. File inventory in `manifest.files` MUST be lexicographically sorted by canonical path.
3. Archive entries MUST have fixed metadata:
- `mtime`: `2026-01-01T00:00:00Z`
- `uid/gid`: `0/0`
- file mode `0644`, directory mode `0755`
4. Digests MUST be lowercase SHA-256 hex.
5. Optional artifacts (`merged_vex.json`, `components.parquet`) MUST not change ordering of required files.
6. Compression toolchain versions MUST be pinned in release manifests.
## Canonicalization conformance tests (required)
- Nested object key ordering stability.
- Unicode normalization and escaping stability.
- Non-finite number rejection (`NaN`, `Infinity`).
- DSSE payload preimage digest stability across repeated runs.
## Byte stability gate
- CI must generate the same pack twice from identical frozen input fixtures.
- Outputs must be byte-identical (`sha256sum pack1 == pack2`).
- On mismatch, pipeline fails with `ERR_PACK_NON_DETERMINISTIC`.
## Deterministic fixture layout
- `testvectors/portable-audit-pack/minimal/`
- `testvectors/portable-audit-pack/with-vex/`
- `testvectors/portable-audit-pack/with-parquet/`
Each fixture set should include:
- inputs (`sbom.json`, optional `vex.json`)
- expected canonical files
- expected per-file SHA-256 digests
- expected package archive digest
## Toolchain pin set (to be implemented)
- JCS canonicalizer version
- DSSE signer library version
- tar implementation/version
- compression implementation/version
- Parquet writer version (if profile enabled)

View File

@@ -0,0 +1,43 @@
# Portable Audit Pack Parquet Profile (Optional)
Status: Optional profile contract for implementation handoff (2026-02-10).
## Positioning
`components.parquet` is optional and must not be required for baseline pack verification.
## Manifest integration
When present, `manifest.files["components.parquet"]` must include:
- `sha256`
- `size`
- `content_type` = `application/x-parquet`
- `compression` = `snappy`
- `schema_fingerprint`
## Recommended schema columns
- `package_name` (STRING)
- `package_version` (STRING)
- `purl` (STRING)
- `license` (STRING)
- `component_hash_sha256` (STRING)
- `artifact_digest_sha256` (STRING)
- `cve_id` (STRING, nullable)
- `vex_status` (STRING, nullable)
- `introduced_range` (STRING, nullable)
- `fixed_version` (STRING, nullable)
- `source_bom_sha256` (STRING)
## Determinism rules
- Stable row ordering: `(artifact_digest_sha256, package_name, package_version, purl)`.
- Stable column ordering exactly as listed above.
- Stable Parquet writer settings pinned by version and compression codec.
- `schema_fingerprint` must be reproducible from logical schema definition.
## Feature gating
- Default profile: disabled.
- Enable only with explicit profile flag.
- Verification ignores Parquet content when absent.
- Verification fails with `ERR_PARQUET_FINGERPRINT_MISMATCH` when present but invalid.
## Operator guidance
- Use Parquet profile for fleet-level offline analytics.
- Keep analytics ingestion separate from baseline release gate verification.

View File

@@ -0,0 +1,40 @@
# Portable Audit Pack Rekor Offline Verification Profile
Status: Draft frozen for implementation handoff (2026-02-10).
## Required Rekor material in pack
At least one of:
- `rekor/tile.tar`
- `rekor/tiles.bundle`
And manifest references:
- `rekor.log_id`
- `rekor.api_version` (`2`)
- `rekor.tile_refs[]`
- `rekor.root_hash`
## Offline verification flow
1. Validate manifest signature and manifest file inventory/digests.
2. Load bundled tile material referenced by `rekor.tile_refs[]`.
3. Reconstruct inclusion proof path for covered digests.
4. Validate Merkle root equals `rekor.root_hash`.
5. Validate checkpoint key material from `verifiers.rekor_pub` when present.
6. Fail closed on any missing tile/proof/checkpoint dependency.
## Stable failure codes
- `ERR_REKOR_TILE_MISSING`
- `ERR_REKOR_TILE_DIGEST_MISMATCH`
- `ERR_REKOR_PROOF_INVALID`
- `ERR_REKOR_CHECKPOINT_INVALID`
- `ERR_REKOR_ROOT_MISMATCH`
- `ERR_REKOR_REFERENCE_UNCOVERED`
## Tamper test requirements
- Corrupt one tile byte -> `ERR_REKOR_TILE_DIGEST_MISMATCH`.
- Modify inclusion path node -> `ERR_REKOR_PROOF_INVALID`.
- Alter checkpoint signature -> `ERR_REKOR_CHECKPOINT_INVALID`.
- Alter `rekor.root_hash` in manifest -> `ERR_REKOR_ROOT_MISMATCH`.
## Compatibility notes
- Existing Rekor receipt contracts remain valid for legacy bundle profiles.
- Portable profile requires deterministic file references under `rekor/` in the manifest.

View File

@@ -0,0 +1,31 @@
# Portable Audit Pack Verification Test Matrix
Status: QA handoff matrix for implementation sprint (2026-02-10).
## Coverage matrix
| ID | Layer | Scenario | Expected result |
| --- | --- | --- | --- |
| PAP-T01 | Unit | Manifest canonicalization stable for nested objects/unicode | PASS |
| PAP-T02 | Unit | Manifest missing required field | `ERR_MANIFEST_SCHEMA` |
| PAP-T03 | Unit | Manifest signature mismatch | `ERR_MANIFEST_SIGNATURE` |
| PAP-T04 | Unit | DSSE payload digest mismatch | `ERR_DSSE_PAYLOAD_DIGEST` |
| PAP-T05 | Unit | File digest mismatch for required file | `ERR_FILE_DIGEST_MISMATCH` |
| PAP-T06 | Integration | Rekor tile corruption | `ERR_REKOR_TILE_DIGEST_MISMATCH` |
| PAP-T07 | Integration | Rekor proof node corruption | `ERR_REKOR_PROOF_INVALID` |
| PAP-T08 | Integration | Checkpoint signature corruption | `ERR_REKOR_CHECKPOINT_INVALID` |
| PAP-T09 | Integration | Root hash mismatch | `ERR_REKOR_ROOT_MISMATCH` |
| PAP-T10 | Integration | Required Rekor material missing | `ERR_REKOR_TILE_MISSING` |
| PAP-T11 | E2E | Full offline verification with valid pack | PASS |
| PAP-T12 | E2E | Repeat generation from frozen input twice | identical SHA-256 output |
| PAP-T13 | E2E | Optional Parquet absent | PASS |
| PAP-T14 | E2E | Optional Parquet present with invalid fingerprint | `ERR_PARQUET_FINGERPRINT_MISMATCH` |
## Fixture expectations
- Golden fixtures under `testvectors/portable-audit-pack/`.
- Expected digests tracked in fixture metadata and CI assertions.
- All fixtures must be network-independent and deterministic.
## Execution log template
| Date (UTC) | Fixture set | Command | Result | Owner |
| --- | --- | --- | --- | --- |
| 2026-02-10 | Planning only | Matrix drafted for implementation sprint handoff. | N/A | QA/Test Automation |

View File

@@ -0,0 +1,95 @@
# Promotion Evidence Contract
## Purpose
This contract defines the evidence payload that promotion gates consume. It freezes
ownership boundaries and required fields for deterministic and offline-capable
release decisions.
## Ownership Boundaries
| Capability | Owning module | Notes |
| --- | --- | --- |
| Evidence storage and retrieval | EvidenceLocker | Stores immutable evidence; does not decide allow/deny. |
| DSSE signing | Signer | Produces signed envelopes and signer metadata. |
| Transparency logging and proof material | Attestor | Produces Rekor UUID/log index/proof references and verifies proofs. |
| PASS/FAIL policy decisioning | Policy Engine | Evaluates gate logic and emits decision outputs. |
| Promotion orchestration | Release Orchestrator | Consumes evidence + policy outputs to progress promotion state. |
## Canonical Promotion Gate Input
The promotion gate input MUST be serializable as canonical JSON with stable
key order and UTC timestamps.
```json
{
"artifact": {
"artifactId": "string",
"digest": "sha256:..."
},
"evidence": {
"evidenceScore": "lowercase-hex-sha256",
"bundleId": "guid",
"bundleDigest": "sha256:..."
},
"sbom": {
"canonicalDigest": "sha256:...",
"format": "cyclonedx|spdx"
},
"attestations": [
{
"predicateType": "string",
"dsseDigest": "sha256:...",
"signerKeyId": "string"
}
],
"transparency": {
"rekorUuid": "string",
"logIndex": 0,
"proofRef": "cas://..."
},
"vex": {
"mergedDigest": "sha256:...",
"statusSummary": "affected|not_affected|under_investigation|mixed"
},
"inToto": {
"layoutDigest": "sha256:...",
"linkDigests": ["sha256:..."]
}
}
```
## EvidenceLocker API Mapping
| Endpoint | Contract fields populated |
| --- | --- |
| `POST /evidence` | `artifact.*`, `evidence.evidenceScore` |
| `GET /evidence/score?artifact_id=...` | `evidence.evidenceScore` |
| `POST /evidence/snapshot` | `evidence.bundleId`, `evidence.bundleDigest` |
| `GET /evidence/{bundleId}` | `sbom.*`, `attestations[]`, `vex.*`, `inToto.*` |
| `POST /evidence/verify` | `transparency.*` verification status and proof linkage |
| `GET /evidence/{bundleId}/portable` | Offline bundle material for air-gapped verification |
## Determinism Requirements
- Serialize gate input with stable ordering and invariant casing.
- Use UTC RFC3339 timestamps only.
- Sort all arrays that do not carry semantic order by deterministic key:
- `attestations[]` by `predicateType`, then `dsseDigest`
- `inToto.linkDigests[]` lexicographically
- Treat digest values as lowercase.
- Fail closed if required evidence fields are missing.
## Offline Verification Requirements
- Promotion gates MUST accept proof references from offline bundles.
- Rekor verification may use tile/proof material from local mirrors.
- If transparency data is unavailable, gate outcome must be explicit policy output
(for example deny, or break-glass path with auditable reason).
## Implementation References
- EvidenceLocker architecture: `docs/modules/evidence-locker/architecture.md`
- EvidenceLocker attestation contract: `docs/modules/evidence-locker/attestation-contract.md`
- Policy ownership contract: `docs/modules/policy/promotion-gate-ownership-contract.md`
- Release Orchestrator runtime gap plan: `docs/modules/release-orchestrator/promotion-runtime-gap-closure-plan.md`

View File

@@ -0,0 +1,331 @@
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"$id": "https://stellaops.io/schemas/evidence-locker/portable-audit-pack-manifest.v1.schema.json",
"title": "StellaOps Portable Audit Pack Manifest v1",
"type": "object",
"additionalProperties": false,
"required": [
"spec_version",
"created_utc",
"artifact",
"files",
"digests",
"rekor",
"timestamps",
"verifiers"
],
"properties": {
"spec_version": {
"type": "string",
"const": "1.0"
},
"created_utc": {
"type": "string",
"format": "date-time"
},
"artifact": {
"$ref": "#/$defs/artifact"
},
"files": {
"type": "object",
"minProperties": 3,
"required": [
"canonical_bom.json",
"dsse_envelope.json",
"manifest.sig"
],
"propertyNames": {
"type": "string",
"minLength": 1,
"pattern": "^[^\\\\]+$"
},
"additionalProperties": {
"$ref": "#/$defs/fileEntry"
}
},
"digests": {
"$ref": "#/$defs/digests"
},
"rekor": {
"$ref": "#/$defs/rekor"
},
"timestamps": {
"$ref": "#/$defs/timestamps"
},
"verifiers": {
"$ref": "#/$defs/verifiers"
},
"compatibility": {
"$ref": "#/$defs/compatibility"
}
},
"$defs": {
"sha256": {
"type": "string",
"pattern": "^[a-f0-9]{64}$"
},
"artifact": {
"type": "object",
"additionalProperties": false,
"required": [
"name",
"version",
"digest",
"media_type"
],
"properties": {
"name": {
"type": "string",
"minLength": 1
},
"version": {
"type": "string",
"minLength": 1
},
"digest": {
"type": "object",
"additionalProperties": false,
"required": [
"sha256"
],
"properties": {
"sha256": {
"$ref": "#/$defs/sha256"
}
}
},
"media_type": {
"type": "string",
"minLength": 1
}
}
},
"fileEntry": {
"type": "object",
"additionalProperties": false,
"required": [
"sha256",
"size",
"content_type"
],
"properties": {
"sha256": {
"$ref": "#/$defs/sha256"
},
"size": {
"type": "integer",
"minimum": 0
},
"content_type": {
"type": "string",
"minLength": 1
},
"compression": {
"type": "string",
"enum": [
"none",
"gzip",
"zstd",
"snappy"
]
},
"schema_fingerprint": {
"type": "string",
"minLength": 1
}
}
},
"digests": {
"type": "object",
"additionalProperties": false,
"required": [
"canonical_bom_sha256",
"dsse_payload_digest"
],
"properties": {
"canonical_bom_sha256": {
"$ref": "#/$defs/sha256"
},
"dsse_payload_digest": {
"type": "object",
"additionalProperties": false,
"required": [
"sha256"
],
"properties": {
"sha256": {
"$ref": "#/$defs/sha256"
}
}
}
}
},
"rekor": {
"type": "object",
"additionalProperties": false,
"required": [
"log_id",
"api_version",
"tile_refs",
"root_hash"
],
"properties": {
"log_id": {
"type": "string",
"minLength": 1
},
"api_version": {
"type": "string",
"const": "2"
},
"tile_refs": {
"type": "array",
"minItems": 1,
"items": {
"type": "object",
"additionalProperties": false,
"required": [
"path",
"covers"
],
"properties": {
"path": {
"type": "string",
"pattern": "^rekor/"
},
"covers": {
"type": "array",
"minItems": 1,
"items": {
"type": "string",
"pattern": "^SHA256:[A-Fa-f0-9]{64}$"
}
}
}
}
},
"root_hash": {
"$ref": "#/$defs/sha256"
}
}
},
"timestamps": {
"type": "object",
"additionalProperties": false,
"required": [
"bom_canonicalized",
"dsse_signed",
"rekor_included"
],
"properties": {
"bom_canonicalized": {
"type": "string",
"format": "date-time"
},
"dsse_signed": {
"type": "string",
"format": "date-time"
},
"rekor_included": {
"type": "string",
"format": "date-time"
}
}
},
"verifiers": {
"type": "object",
"additionalProperties": false,
"required": [
"pubkeys"
],
"properties": {
"pubkeys": {
"type": "array",
"minItems": 1,
"items": {
"$ref": "#/$defs/pubkey"
}
},
"rekor_pub": {
"type": "object",
"additionalProperties": false,
"required": [
"type",
"key_material"
],
"properties": {
"type": {
"type": "string",
"enum": [
"rekor-checkpoint",
"rekor-key-hash"
]
},
"key_material": {
"type": "string",
"minLength": 1
}
}
}
}
},
"pubkey": {
"type": "object",
"additionalProperties": false,
"required": [
"id",
"type",
"public_key",
"usage"
],
"properties": {
"id": {
"type": "string",
"minLength": 1
},
"type": {
"type": "string",
"enum": [
"ed25519",
"ecdsa-p256",
"rsa-4096"
]
},
"public_key": {
"type": "string",
"minLength": 1
},
"usage": {
"type": "array",
"minItems": 1,
"items": {
"type": "string",
"enum": [
"dsse",
"manifest-signing",
"checkpoint-verification"
]
}
}
}
},
"compatibility": {
"type": "object",
"additionalProperties": false,
"properties": {
"legacy_manifest_version": {
"type": "string"
},
"legacy_bundle_id": {
"type": "string"
},
"migration_notes": {
"type": "array",
"items": {
"type": "string"
}
}
}
}
}
}