docs: module dossier + install/quickstart sync for truthful cutover sprints

- API_CLI_REFERENCE.md, INSTALL_GUIDE.md, quickstart.md, architecture/integrations.md, dev/DEV_ENVIRONMENT_SETUP.md, integrations/LOCAL_SERVICES.md: reflect real-service wiring.
- docs/modules/**: module dossier updates across the modules touched by SPRINT_20260415_001..007 + SPRINT_20260416_003..017 + SPRINT_20260417_018..024 + SPRINT_20260418_025 + SPRINT_20260419_026.
- docs/features/checked/web/**: update feature notes where UI changed.
- docs/qa/feature-checks/runs/web/evidence-presentation-ux/: QA evidence artifacts.
- docs/setup/**, docs/technical/**: align with setup wizard contracts.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
master
2026-04-19 14:45:09 +03:00
parent ad62ba7f76
commit fdf95e0f46
67 changed files with 590 additions and 360 deletions

View File

@@ -7,6 +7,7 @@ Attestor converts signed DSSE evidence from the Signer into transparency-log pro
- Sprint tracker `docs/implplan/SPRINT_0313_0001_0001_docs_modules_attestor.md` and module `TASKS.md` added to mirror status.
- Observability runbook stub + dashboard placeholder added under `operations/` (offline import) pending next demo outputs.
- Platform Events samples (2025-10-18/19) remain the current canonical `attestor.logged@1`; keep verification workflows aligned.
- 2026-04-16: live Attestor runtime cut over to PostgreSQL-backed canonical attestation entry storage, PostgreSQL-backed watchlist storage, and truthful non-testing `501` behavior for bulk verification until a durable worker/store path exists.
## Why it exists
- **Evidence first:** organisations need portable, verifiable attestations that prove build provenance, SBOM availability, policy verdicts, and VEX statements.
@@ -38,13 +39,13 @@ All predicates capture subjects, issuer metadata, policy context, materials, opt
- All verification/list APIs share the token-bucket rate limiter (`quotas.perCaller`) in addition to the existing submission limiter.
## UI, CLI, and SDK workflows
- **Console:** Evidence browser, verification reports, chain-of-custody graph, issuer/key management, attestation workbench, and bulk verification flows.
- **Console:** Evidence browser, verification reports, chain-of-custody graph, issuer/key management, attestation workbench, and bulk verification surfaces. Outside `Testing`, bulk verification currently returns truthful `501` until a durable worker/store path ships.
- **CLI / SDK:** `stella attest sign|verify|list|fetch|key` commands plus language SDKs to integrate build pipelines and offline verification scripts.
- **Policy Studio:** Verification policies author required predicate types, issuers, witness requirements, and freshness windows; simulations show enforcement impact.
Reference: `docs/modules/attestor/guides/timestamp-policy.md` for RFC-3161 policy assertions.
## Storage, offline & air-gap posture
- PostgreSQL stores entry metadata, dedupe keys, and audit events; object storage optionally archives DSSE bundles.
- PostgreSQL stores canonical attestation entries in `attestor.entries`, watchlist state in `attestor.identity_watchlist` / `attestor.identity_alert_dedup`, and audit events in `proofchain.audit_log`; startup migrations are the runtime authority.
- Export Center packages attestation bundles (`stella export attestation-bundle`) for Offline Kit delivery.
- Transparency logs can be mirrored; offline mode records gaps and provides compensating controls.

View File

@@ -120,20 +120,27 @@ Database: `attestor`
```sql
CREATE TABLE attestor.entries (
id UUID PRIMARY KEY, -- rekor-uuid
rekor_uuid TEXT PRIMARY KEY,
bundle_sha256 TEXT NOT NULL UNIQUE,
artifact_sha256 TEXT NOT NULL,
artifact_kind TEXT NOT NULL, -- sbom|report|vex-export
artifact_kind TEXT NOT NULL, -- sbom|report|vex-export|policy-eval
artifact_image_digest TEXT,
artifact_subject_uri TEXT,
bundle_sha256 TEXT NOT NULL, -- canonicalized DSSE
log_index INTEGER, -- log index/sequence if provided by backend
proof_checkpoint JSONB, -- { origin, size, rootHash, timestamp }
proof_inclusion JSONB, -- { leafHash, path[] } Merkle path (tiles)
log_url TEXT,
log_index BIGINT,
log_backend TEXT NOT NULL,
log_url TEXT NOT NULL,
log_id TEXT,
log_integrated_time BIGINT,
created_at TIMESTAMPTZ DEFAULT NOW(),
updated_at TIMESTAMPTZ DEFAULT NOW(),
status TEXT NOT NULL, -- included|pending|failed
signer_identity JSONB -- { mode, issuer, san?, kid? }
signer_mode TEXT NOT NULL,
signer_issuer TEXT,
signer_subject_alternative_name TEXT,
signer_key_id TEXT,
proof JSONB, -- canonical Rekor checkpoint + inclusion proof
witness JSONB,
mirror JSONB
);
```
@@ -148,27 +155,27 @@ Database: `attestor`
);
```
* `audit` table
* `audit log` table
```sql
CREATE TABLE attestor.audit (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
ts TIMESTAMPTZ DEFAULT NOW(),
caller_cn TEXT,
caller_mtls_thumbprint TEXT,
caller_sub TEXT,
caller_aud TEXT,
action TEXT NOT NULL, -- submit|verify|fetch
artifact_sha256 TEXT,
bundle_sha256 TEXT,
rekor_uuid UUID,
log_index INTEGER,
result TEXT NOT NULL,
latency_ms INTEGER,
backend TEXT
CREATE TABLE proofchain.audit_log (
log_id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
operation TEXT NOT NULL,
entity_type TEXT NOT NULL,
entity_id TEXT NOT NULL,
actor TEXT,
details JSONB,
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW()
);
```
* `watchlist` tables
```sql
CREATE TABLE attestor.identity_watchlist (...);
CREATE TABLE attestor.identity_alert_dedup (...);
```
Indexes:
* `entries`: indexes on `artifact_sha256`, `bundle_sha256`, `created_at`, and composite `(status, created_at DESC)`.
@@ -506,9 +513,13 @@ The exception signing service provides endpoints for signing, verifying, and ren
### 4.5 Bulk verification
`POST /api/v1/rekor/verify:bulk` enqueues a verification job containing up to `quotas.bulk.maxItemsPerJob` items. Each item mirrors the single verification payload (uuid | artifactSha256 | subject+envelopeId, optional policyVersion/refreshProof). The handler persists a PostgreSQL job record (`bulk_jobs` table) and returns `202 Accepted` with a job descriptor and polling URL.
Note (2026-04-16): non-testing runtime now returns truthful `501 Not Implemented` for the bulk verification endpoints until a durable bulk job store plus worker path exists. The previous in-memory queue behavior is test-only.
`GET /api/v1/rekor/verify:bulk/{jobId}` returns progress and per-item results (subject/uuid, status, issues, cached verification report if available). Jobs are tenant- and subject-scoped; only the initiating principal can read their progress.
Historical design note below is retained for the future durable implementation. It is not the current live host behavior.
When the durable worker ships, `POST /api/v1/rekor/verify:bulk` should enqueue a verification job containing up to `quotas.bulk.maxItemsPerJob` items and return `202 Accepted` with a job descriptor plus polling URL.
When the durable worker ships, `GET /api/v1/rekor/verify:bulk/{jobId}` should return progress and per-item results (subject/uuid, status, issues, cached verification report if available). Jobs remain tenant- and subject-scoped; only the initiating principal can read their progress.
**Worker path:** `BulkVerificationWorker` claims queued jobs (`status=queued → running`), executes items sequentially through the cached verification service, updates progress counters, and records metrics:
@@ -935,6 +946,8 @@ The Attestor provides proactive monitoring for signing identities appearing in t
Authorization for the live watchlist surface follows the canonical trust scope family (`trust:read`, `trust:write`, `trust:admin`). The service still accepts legacy `watchlist:*` aliases for backward compatibility, but new clients and UI sessions should rely on the trust scopes.
Non-testing runtime persists watchlist state in PostgreSQL (`attestor.identity_watchlist`, `attestor.identity_alert_dedup`) and reserves in-memory watchlist storage for test harnesses only.
### Event Flow
```
@@ -2695,17 +2708,17 @@ Source consolidation places all trust-domain code under a single directory for o
| Attestation evidence (proofchain, inclusion proofs, Rekor entries) | Attestor | `attestor` PostgreSQL schema | High -- tamper-evident, integrity-critical |
| Provenance evidence (SLSA predicates, build attestations, Merkle trees) | Provenance (library) | Consumed by Attestor/EvidenceLocker | High -- deterministic, reproducible |
| Signer metadata (audit events, signing ceremony state, rate limits) | Signer | `signer` PostgreSQL schema | High -- operational security |
| Signer key material (KMS/HSM refs, Fulcio certs, trust anchors, rotation state) | Signer (KeyManagement) | `key_management` PostgreSQL schema | Critical -- cryptographic trust root |
| Signer key material (KMS/HSM refs, Fulcio certs, trust anchors, rotation state) | Signer (KeyManagement) | `signer` PostgreSQL schema | Critical -- cryptographic trust root |
### PostgreSQL Schema Ownership
Each trust-domain service retains its own DbContext and dedicated PostgreSQL schema:
- **`attestor` schema** -- Owned by the Attestor service. Contains `entries`, `dedupe`, `audit` tables for transparency log state.
- **`signer` schema** -- Owned by the Signer service. Contains signing ceremony audit, rate limit state, and operational metadata.
- **`key_management` schema** -- Owned by the Signer KeyManagement library. Contains key rotation records, trust anchor configurations, and HSM/KMS binding metadata.
- **`signer` schema** -- Owned by the Signer trust-domain runtime. Contains ceremony state/audit plus key-management tables (`trust_anchors`, `key_history`, `key_audit_log`) that the live Signer host auto-migrates on startup.
- **KeyManagement library boundary** -- Key rotation, trust anchor management, and HSM/KMS binding logic remain isolated in the `StellaOps.Signer.KeyManagement` library, but the canonical runtime tables now live inside the `signer` schema rather than a separate `key_management` schema.
There is **no cross-schema merge**. Each service connects with its own connection string scoped to its own schema.
There is **no cross-service schema merge**. Attestor evidence state remains isolated from Signer runtime state, and the Signer host now requires a real KeyManagement connection string outside `Testing`. The stub bearer path is test-only and is not part of the live composition root.
### Security Boundary: No-Merge Decision (ADR)

View File

@@ -4,11 +4,13 @@
Provide a concise, living plan for Attestor feature delivery, timestamping, and offline verification workflows.
## Active work
- `docs/implplan/SPRINT_20260416_017_Attestor_truthful_runtime_storage_cutover.md`
- `docs/implplan/SPRINT_20260119_010_Attestor_tst_integration.md`
- `docs/implplan/SPRINT_20260119_013_Attestor_cyclonedx_1.7_generation.md`
- `docs/implplan/SPRINT_20260119_014_Attestor_spdx_3.0.1_generation.md`
## Near-term deliverables
- Durable bulk verification worker/store path to replace the current truthful non-testing `501` unsupported runtime.
- RFC-3161 timestamping integration (signing, verification, policy context).
- CycloneDX 1.7 predicate writer updates and determinism tests.
- SPDX 3.0.1 predicate writer updates and determinism tests.
@@ -20,6 +22,7 @@ Provide a concise, living plan for Attestor feature delivery, timestamping, and
- Policy evaluation integration for timestamp assertions.
## Evidence of completion
- PostgreSQL-backed runtime proof tests for canonical entry/audit storage and watchlist persistence under `src/Attestor/StellaOps.Attestor/StellaOps.Attestor.Tests/Integration/AttestorTruthfulRuntimeTests.cs`.
- Attestor timestamping library changes under `src/Attestor/__Libraries/`.
- Updated CLI command handlers and tests under `src/Cli/`.
- Deterministic unit tests and fixtures in `src/Attestor/__Tests/`.