CDEvents increasingly feed supply-chain decisions (SLSA gates, release approval, audit), but a CDEvent is only as trustworthy as the store it sits in: the same key can re-sign, and a server-side log can be rewritten after the fact. CloudEvents left data integrity to extensions (integrity issues #143 and #565 were closed as out of core scope), so there is a clean seam at the CDEvents layer.
Here is a small, working example of one additive way to close it. The CDEvent carries two optional CloudEvents extension attributes:
markovianroot: the RFC 8785 (JCS) SHA-256 root of the event's data, committed to an append-only, Bitcoin-anchored log;
markovianverify: a public endpoint that confirms that root, no account, no key.
A consumer recomputes the root from data and checks it against Bitcoin block headers. It proves the event existed at a point in time and was not altered, attested by a party the operator does not control. It does not assert the build or artifact is correct; that stays a separate concern (SLSA, in-toto).
Worked, independently verifiable example (a real dev.cdevents.artifact.published event, live on-chain commitment):
{
"id": "3e4ed1e0-81cd-4f9d-a4ea-c2318cabd8ca",
"source": "/cd/pipeline/release-build",
"type": "dev.cdevents.artifact.published.0.2.0",
"specversion": "1.0",
"time": "2026-07-03T09:15:00Z",
"datacontenttype": "application/json",
"markovianroot": "919f2566d52d49a618868a970f3f98eb0bf630ad02c81ca6ed5432e377f03fbf",
"markovianverify": "https://api.quantsynth.net/verify/919f2566d52d49a618868a970f3f98eb0bf630ad02c81ca6ed5432e377f03fbf",
"data": {
"context": { "version": "0.4.1", "id": "6f5817b6-ce9e-49cf-954a-5f10b1ad637b", "source": "/cd/pipeline/release-build", "type": "dev.cdevents.artifact.published.0.2.0", "timestamp": "2026-07-03T09:15:00Z" },
"subject": { "id": "pkg:oci/example-service@sha256:5b0e...c14a", "source": "/cd/pipeline/release-build", "type": "artifact", "content": { "user": "ci-runner", "sbom": { "uri": "https://artifacts.example.com/example-service/sbom.spdx.json" } } }
}
}
Verify it yourself: RFC 8785-canonicalize the data, sha256 it, and confirm it equals the data_hash returned at the markovianverify URL (returns verified: true, committed at block 140129). No calendar, no issuer, no trust in the emitting pipeline.
Two honest notes: it is additive and optional (nothing in the core CDEvent changes), and I am not proposing it as a requirement, just showing a working shape in case event-level tamper-evidence is on the roadmap for the SLSA/audit users. Happy to adapt the attribute names or format to CDEvents conventions, or move this to a Discussion if that is the better venue. A runnable stamp-and-verify script is available if useful.
CDEvents increasingly feed supply-chain decisions (SLSA gates, release approval, audit), but a CDEvent is only as trustworthy as the store it sits in: the same key can re-sign, and a server-side log can be rewritten after the fact. CloudEvents left data integrity to extensions (integrity issues #143 and #565 were closed as out of core scope), so there is a clean seam at the CDEvents layer.
Here is a small, working example of one additive way to close it. The CDEvent carries two optional CloudEvents extension attributes:
markovianroot: the RFC 8785 (JCS) SHA-256 root of the event'sdata, committed to an append-only, Bitcoin-anchored log;markovianverify: a public endpoint that confirms that root, no account, no key.A consumer recomputes the root from
dataand checks it against Bitcoin block headers. It proves the event existed at a point in time and was not altered, attested by a party the operator does not control. It does not assert the build or artifact is correct; that stays a separate concern (SLSA, in-toto).Worked, independently verifiable example (a real
dev.cdevents.artifact.publishedevent, live on-chain commitment):{ "id": "3e4ed1e0-81cd-4f9d-a4ea-c2318cabd8ca", "source": "/cd/pipeline/release-build", "type": "dev.cdevents.artifact.published.0.2.0", "specversion": "1.0", "time": "2026-07-03T09:15:00Z", "datacontenttype": "application/json", "markovianroot": "919f2566d52d49a618868a970f3f98eb0bf630ad02c81ca6ed5432e377f03fbf", "markovianverify": "https://api.quantsynth.net/verify/919f2566d52d49a618868a970f3f98eb0bf630ad02c81ca6ed5432e377f03fbf", "data": { "context": { "version": "0.4.1", "id": "6f5817b6-ce9e-49cf-954a-5f10b1ad637b", "source": "/cd/pipeline/release-build", "type": "dev.cdevents.artifact.published.0.2.0", "timestamp": "2026-07-03T09:15:00Z" }, "subject": { "id": "pkg:oci/example-service@sha256:5b0e...c14a", "source": "/cd/pipeline/release-build", "type": "artifact", "content": { "user": "ci-runner", "sbom": { "uri": "https://artifacts.example.com/example-service/sbom.spdx.json" } } } } }Verify it yourself: RFC 8785-canonicalize the
data,sha256it, and confirm it equals thedata_hashreturned at themarkovianverifyURL (returnsverified: true, committed at block 140129). No calendar, no issuer, no trust in the emitting pipeline.Two honest notes: it is additive and optional (nothing in the core CDEvent changes), and I am not proposing it as a requirement, just showing a working shape in case event-level tamper-evidence is on the roadmap for the SLSA/audit users. Happy to adapt the attribute names or format to CDEvents conventions, or move this to a Discussion if that is the better venue. A runnable stamp-and-verify script is available if useful.