CRA Conformity Dossier v1
Contract ID: CONTRACT-CRA-CONFORMITY-DOSSIER-V1-029 Status: Implemented (v1) Owner: ExportCenter Last Updated: 2026-05-30
Implementation: src/ExportCenter/StellaOps.ExportCenter.Adapters.Cra/ConformityDossierAdapter.cs, ConformityDossierModels.cs. CLI surface: src/Cli/StellaOps.Cli/Commands/ConformityDossierCommandGroup.cs (wired as stella export conformity-dossier). EU signing registry entry: src/Attestor/StellaOps.Signer/StellaOps.Signer.Core/EuSigningContracts.cs (EuSigningPayloadRegistry.CraConformityDossier).
Purpose
conformity-dossier-v1 defines the deterministic bundle index and overlay files used by ExportCenter to assemble CRA (EU Cyber Resilience Act) conformity-assessment dossiers. The dossier composes the CRA Annex VII technical file from cra-tech-file-v1and adds the selected conformity-route overlay:
- Module A: internal production control / self-assessment.
- Module B+C: EU type-examination plus production conformity.
- Module H: full quality management system.
CRA-Q5 sets Module A as the default route for Stella itself. B+C and H remain supported for customer products or future SKUs that require a stricter route.
The dossier inherits the embedded technical file’s EU declaration of conformity (Annex V) lifecycle from cra-tech-file-v1: Stella generates an operator-completable DoC template (status template, fail-closed) and embeds the operator’s own signed declaration (status operator-signed, validated through ICryptoProviderRegistry/ICryptoSigner and bound by hash); the legacy stub value is retired. Stella never authors or signs a legal DoC on the operator’s behalf. The overlay stub status below is a separate overlay-completeness concept, unrelated to the DoC lifecycle.
Audience: ExportCenter engineers and regulatory-export operators producing CRA conformity dossiers, plus auditors verifying a dossier offline. Every structural claim below is grounded in the adapter source cited in the header; the cra-tech-file-v1contract covers the embedded technical file.
Schema Pinning
index.jsonschemaVersionMUST be exactlyconformity-dossier-v1(ConformityDossierConstants.SchemaVersion).- Overlay documents (
overlays/**/*.json) carry their ownschemaVersionofconformity-dossier-overlay-v1(ConformityDossierConstants.OverlaySchemaVersion). - The materialization audit event carries
schemaVersionconformity-dossier-audit-event-v1(ConformityDossierConstants.AuditEventSchemaVersion). - EU signing payload registry id:
conformity-dossier-v1(docs/contracts/eu-signing-payload-registry-v1.md;EuSigningPayloadRegistry.CraConformityDossier). The registry pins payload typeapplication/vnd.stellaops.cra.conformity-dossier.index.v1+json, schema-pin idconformity-dossier-v1, expected signer profiletenant-regulatory-export, and schema-pin JSON pathschemaVersion. - Producers MUST NOT auto-upgrade this contract when later CRA harmonised standards land. A future
conformity-dossier-v2is required for breaking overlay, evidence, or signing changes. moduleMUST be one ofA,B+C, orH(ConformityDossierConstants.ModuleA,ModuleBc=B+C,ModuleH). The adapter normalizes case and whitespace and also accepts the aliasesBC,moduleA,moduleB+C,moduleBC,moduleH.- All hashes MUST be lowercase SHA-256 with the
sha256:prefix. The adapter strips/lowers an incomingsha256:prefix and rejects any digest that is not exactly 64 lower-hex chars. - JSON payloads MUST be canonicalized with ordinal-sorted object keys and UTF-8 without a BOM (
StellaOps.Canonical.Json.CanonJson.Canonicalize). - Tar entries MUST use the same deterministic metadata as
cra-tech-file-v1: PAX format, fixed mtime2025-01-01T00:00:00Z, uid/gid0, empty user/group names, fixed POSIX mode0644(rw-r--r--), and a gzip header MTIME pinned to the same fixed timestamp (CraDeterministicArchive).
Adapter And Media Types
| Identifier | Value | Source |
|---|---|---|
| Adapter id | cra:conformity-dossier | ConformityDossierConstants.AdapterId |
| Display name | CRA Conformity Assessment Dossier | ConformityDossierAdapter.DisplayName |
| Index payload type | application/vnd.stellaops.cra.conformity-dossier.index.v1+json | IndexPayloadType |
| Bundle media type | application/vnd.stellaops.cra.conformity-dossier.v1+tar+gzip | BundleMediaType |
| Overlay media type | application/vnd.stellaops.cra.conformity-dossier.overlay.v1+json | OverlayMediaType |
| Embedded tech-file path | tech-file/cra-tech-file.tar.gz | TechFilePath |
The adapter registers as an IExportAdapter via ConformityDossierAdapterServiceCollectionExtensions.AddConformityDossierAdapter. It declares no SupportedFormats and SupportsStreaming = false (ProcessStreamAsync delegates to ProcessAsync).
Bundle Layout
Every dossier bundle contains:
index.json
checksums.txt
tech-file/cra-tech-file.tar.gz
overlays/common/declared-controls.json
overlays/common/evidence-links.json
overlays/common/audit-signatures.json
Module-specific overlays are selected by module.
Module A:
overlays/module-a/self-assessment.json
Module B+C:
overlays/module-bc/eu-type-examination.json
overlays/module-bc/production-conformity.json
overlays/module-bc/test-certificates.json
Module H:
overlays/module-h/full-qms.json
overlays/module-h/iso27001-control-effectiveness.json
index.json is authoritative. checksums.txt is a deterministic convenience file for offline operators.
Required index.json Fields
| Field | Type | Requirement |
|---|---|---|
schemaVersion | string | MUST equal conformity-dossier-v1. |
generatedAt | RFC3339 timestamp | UTC timestamp chosen by the caller, not wall-clocked inside the adapter. |
module | string | A, B+C, or H. |
route | string | Stable route slug derived from module (ResolveRoute): A → internal-production-control-self-assessment, B+C → eu-type-examination-plus-production-conformity, H → full-quality-management-system. |
product | object | Same product shape as cra-tech-file-v1. |
release | object | Same release shape as cra-tech-file-v1. |
techFile | object | Path, schema version, index hash, bundle hash, and size for the embedded CRA tech file. |
overlays | array | Overlay index entries, ordered by order. |
declaredControls | array | Declared CRA controls and mapped evidence refs. |
evidenceLinks | array | Immutable evidence links used by controls and overlays. |
testCertificates | array | Notified-body or test-certificate refs for B+C where applicable. |
auditSignatures | array | Signature refs for dossier review, approval, or attestation events. |
blockers | array | Missing dependencies that prevent a complete dossier. |
signing | object | Current signing state for the dossier index. |
Each overlays[] entry MUST include:
| Field | Type | Requirement |
|---|---|---|
order | integer | Stable overlay order. |
overlayId | string | Stable overlay identifier. |
title | string | Stable display title. |
path | string | Relative bundle path. |
mediaType | string | MUST be application/vnd.stellaops.cra.conformity-dossier.overlay.v1+json. |
sha256 | string | SHA-256 hash of the overlay file. |
sizeBytes | integer | Overlay byte length. |
status | string | complete, stub, or blocked (see Overlay Status Resolution). |
evidenceLinks | array | Evidence links directly used by this overlay. Populated only for the evidence-links, module-a-self-assessment, module-bc-eu-type-examination, and module-h-full-qms overlays; empty for all others (SelectOverlayEvidenceLinks). |
The overlay ids emitted by the adapter (ConformityDossierConstants) are: declared-controls, evidence-links, audit-signatures (always present); module-a-self-assessment (Module A); module-bc-eu-type-examination, module-bc-production-conformity, module-bc-test-certificates (Module B+C); module-h-full-qms, module-h-iso27001-control-effectiveness (Module H). The common overlays are ordered 1..3; Module A appends order 10; Module B+C appends orders 20..22; Module H appends orders 30..31. index.json.overlays[] is sorted by order.
Overlay Status Resolution
status is computed by ResolveOverlayStatus:
| Overlay id | complete when | otherwise |
|---|---|---|
declared-controls | declared controls present | stub |
evidence-links | evidence links present | stub |
audit-signatures | audit signatures present | stub |
module-a-self-assessment | declared controls AND evidence links present | stub |
module-bc-eu-type-examination | test certificates present | blocked |
module-bc-test-certificates | test certificates present | blocked |
module-bc-production-conformity | audit signatures present | stub |
module-h-full-qms | QMS evidence present | blocked |
module-h-iso27001-control-effectiveness | ISO/IEC 27001 control-effectiveness present | blocked |
Overlay Data Shapes
declaredControls[] entries (ConformityDossierDeclaredControl) contain. status defaults to declared when omitted; the array is de-duplicated and ordinal-sorted by controlId:
{
"controlId": "CRA-SEC-001",
"title": "Secure release evidence control",
"ownerRole": "product-owner",
"craRequirements": ["I.II.2"],
"evidenceRefs": ["evidence://cra/sbom/sbom"],
"status": "declared"
}
evidenceLinks[] entries (ConformityDossierEvidenceLink) contain. sha256 is mandatory and MUST be a valid SHA-256 digest (the adapter throws otherwise); mediaType defaults to application/octet-stream when blank; description is optional; the array is de-duplicated and ordinal-sorted by evidenceId then ref:
{
"evidenceId": "sbom:release",
"kind": "sbom",
"ref": "evidence://bundle/release-2026.04/sbom",
"sha256": "sha256:0000000000000000000000000000000000000000000000000000000000000000",
"mediaType": "application/vnd.cyclonedx+json",
"controlIds": ["CRA-SEC-001"],
"craRequirements": ["I.II.2"],
"description": "Release SBOM"
}
testCertificates[] entries (ConformityDossierTestCertificateRef) are required for complete B+C overlays. expiresOn is an optional DateOnly (yyyy-MM-dd) and is omitted when null; the array is de-duplicated and ordinal-sorted by certificateId:
{
"certificateId": "NB-CRA-2026-0001",
"issuer": "notified-body",
"certificateRef": "evidence://cra/certificates/nb-cra-2026-0001",
"sha256": "sha256:0000000000000000000000000000000000000000000000000000000000000000",
"scope": "product-type",
"expiresOn": "2031-04-30"
}
auditSignatures[] entries (ConformityDossierAuditSignatureRef) identify immutable signature evidence. payloadHash MUST be a valid SHA-256 digest; signedAt is normalized to UTC; the array is de-duplicated and ordinal-sorted by signatureRef:
{
"signerRef": "attestor://signers/export-center",
"signatureRef": "evidence://cra/signatures/conformity-dossier",
"payloadHash": "sha256:0000000000000000000000000000000000000000000000000000000000000000",
"signedAt": "2026-04-30T10:00:00Z",
"purpose": "conformity-dossier"
}
Module H additionally requires two arrays that ride only in the request and in the Module-H overlay documents (they are not surfaced as top-level index.json fields).
qmsEvidence[] (ConformityDossierQmsEvidenceRef) — full quality-management-system process evidence; de-duplicated and ordinal-sorted by processArea then evidenceId:
{
"evidenceId": "qms:sdl",
"processArea": "secure-development-lifecycle",
"evidenceRef": "evidence://cra/qms/sdl",
"sha256": "sha256:0000000000000000000000000000000000000000000000000000000000000000",
"effectiveness": "evidence-present"
}
iso27001ControlEffectiveness[] (ConformityDossierIso27001ControlEffectivenessRef) — ISO/IEC 27001 control-effectiveness slice linked to CRA controls; de-duplicated and ordinal-sorted by iso27001Control then controlId:
{
"controlId": "CRA-SEC-001",
"iso27001Control": "A.8.25",
"effectiveness": "evidence-present",
"evidenceRef": "evidence://cra/iso27001/a-8-25",
"sha256": "sha256:0000000000000000000000000000000000000000000000000000000000000000"
}
Overlay Document Shape
Each overlays/**/*.json file in the bundle is a ConformityDossierOverlayDocument (distinct from the index.json.overlays[] index entry). It carries:
| Field | Type | Notes |
|---|---|---|
schemaVersion | string | Always conformity-dossier-overlay-v1. |
module | string | A, B+C, or H. |
overlayId | string | One of the overlay ids listed above. |
title | string | Stable display title. |
status | string | complete, stub, or blocked. |
generatedAt | RFC3339 | UTC; mirrors the index. |
productRef | string | Product reference (matches index.product.productRef). |
releaseVersion | string | Release version. |
declaredControls | array | Subset selected per overlay (SelectOverlayControls). |
evidenceLinks | array | Subset selected per overlay (SelectOverlayEvidenceLinks). |
testCertificates | array | Populated only for B+C type-examination / test-certificate overlays. |
auditSignatures | array | Populated only for audit-signatures / module-bc-production-conformity. |
qmsEvidence | array | Populated only for module-h-full-qms. |
iso27001ControlEffectiveness | array | Populated only for module-h-iso27001-control-effectiveness. |
notes | array | Deterministic note(s) keyed off status (blocked/stub/complete). |
Module Completion Rules
Blockers are produced by AddModuleBlockers. They are merged with any caller-supplied blockers, de-duplicated by dependency, and ordinal-sorted by dependency in index.json.blockers[]. Each blocker is a CraTechFileDependencyBlocker ({ dependency, reason, sprintRef? }).
Regardless of module, a dossier-audit-signatures blocker is added whenever no audit signatures are supplied (sprintRef SPRINT_20260430_022_Attestor_cadenced_dsse_envelope.md). This reflects that dossier audit signatures are unavailable until DSSE/CAdES signing is wired into ExportCenter.
Module A is complete when declared controls and evidence links are present. It may still carry the dossier-audit-signatures blocker until DSSE/CAdES signing is wired; Module A adds no module-specific blocker.
Module B+C is complete when test certificates are present for EU type examination and audit signatures are present for production conformity. Missing test certificates create a module-bc-test-certificates blocker (no sprintRef).
Module H is complete when QMS evidence and the ISO/IEC 27001 control-effectiveness slice are both present. Missing evidence creates module-h-qms-evidence (no sprintRef) and/or module-h-iso27001-control-effectiveness (sprintRef SPRINT_20260430_080_DOCS_iso27001_mapping.md) blockers.
Signing And Audit
index.json is the intended DSSE payload for the Attestor signing slice. Until DSSE/CAdES support lands, ExportCenter records:
{
"status": "not-signed",
"payloadType": "application/vnd.stellaops.cra.conformity-dossier.index.v1+json",
"blockedBy": "SPRINT_20260430_022_Attestor_cadenced_dsse_envelope.md"
}
The final exporter MUST emit an audit event after the archive hash is known. That event is outside index.json to avoid a self-referential bundle hash. The adapter returns it as ConformityDossierAuditEvent on ConformityDossierBundleResult.AuditEvent:
{
"schemaVersion": "conformity-dossier-audit-event-v1",
"eventType": "cra.conformity_dossier.bundle.materialized",
"occurredAt": "2026-04-30T10:00:00Z",
"module": "A",
"productRef": "tenant:.../conformity-dossier",
"releaseVersion": "unversioned",
"techFileBundleHash": "sha256:...",
"indexHash": "sha256:...",
"bundleHash": "sha256:...",
"signingStatus": "not-signed",
"signerRef": null
}
The index.json techFile object carries { path, schemaVersion, indexHash, bundleHash, sizeBytes } for the embedded tech-file/cra-tech-file.tar.gz (ConformityDossierTechFileRef).
Offline And Replay Expectations
- Deterministic test location:
src/ExportCenter/StellaOps.ExportCenter.Adapters.Cra.Tests/CraTechFileAdapterTests.cs(conformity-dossier facts share this class with the tech-file adapter tests, traitIntent=Regulatory). CLI command coverage:src/Cli/__Tests/StellaOps.Cli.Tests/Commands/ConformityDossierCommandTests.cs. - Tests MUST prove byte-identical Module A output from identical inputs (
ConformityBuild_ModuleA_ProducesDeterministicSelfAssessmentBundleasserts equalBundleHash/IndexHash/BundleBytes) and must cover B+C and H overlay selection. - Verification MUST be possible without network access by recomputing
checksums.txt, validatingindex.json, validating the embeddedtech-file/cra-tech-file.tar.gz, and later verifying the DSSE/CAdES envelope when Attestor support is available. - The dossier MUST preserve immutable evidence refs and MUST NOT copy mutable runtime state into overlays.
CLI Surface
The CLI command stella export conformity-dossier is implemented (ConformityDossierCommandGroup, registered in CommandFactory under the export group; CLI-CRA-023 / SPRINT_20260430_023_ExportCenter_conformity_dossier.md). Options:
| Option | Required | Notes |
|---|---|---|
--module | yes | A, B+C, or H (case/whitespace-normalized; aliases BC, moduleA, etc.). |
--product | yes | Product reference bound into the dossier. |
--input | yes | Path to a conformity-dossier-cli-input-v1 JSON file. |
--output, -o | yes | Path for the deterministic tar.gz bundle. |
--overwrite | no | Overwrite the output file if it exists. |
--json | no | Emit a JSON command summary. |
--verbose | no | Print overlay/blocker counts. |
The --input file is a conformity-dossier-cli-input-v1 envelope (InputSchemaVersion) carrying generatedAt, product, release, evidenceRefs, harmonisedStandards, euDeclarationOfConformity, supportPolicy, sourceRefs, techFileBlockers, declaredControls, evidenceLinks, testCertificates, auditSignatures, qmsEvidence, iso27001ControlEffectiveness, and dossierBlockers. The CLI enforces additional preconditions before building: at least one tech-file evidence ref, at least one declared control, at least one evidence link; Module B+C requires at least one test certificate; Module H requires at least one QMS evidence ref and at least one ISO/IEC 27001 control-effectiveness ref. Exit codes: success, input-file-not-found (missing --input), and general-error (validation failures).
Known v1 Blockers
- Policy-gate frontmatter updates for CRA mappings require Policy documentation ownership and are blocked unless explicitly allowed by a Policy sprint.
- DSSE+CAdES envelope wrapping is owned by Attestor/Signer; the index records
signing.status = not-signed(CraTechFileSigningState) until that slice lands. The EU offline verifier and registry entry forconformity-dossier-v1already exist (EuArtifactOfflineVerifier,EuSigningPayloadRegistry), but the adapter itself does not wrap the index in a DSSE/CAdES envelope.
Related Contracts
- CRA Technical File v1 — the Annex VII technical file embedded at
tech-file/cra-tech-file.tar.gz. - EU Signing Payload Registry v1 — pins the
conformity-dossier-v1payload type, schema, and signer profile.
