Skip to content

Schema fingerprints

A schema fingerprint is the first 12 hex chars of the SHA256 of a verb’s schema file. Every emitted PR includes the fingerprint of the verb that produced it. Fingerprints let you trace any historical PR back to the exact contract version that emitted it.

In every PR body’s metadata block:

petrova:
verb: propose_fix
schema_version: 1
schema_fingerprint: a8b3c4d5e6f7
...

The schema_version field is the major contract version (currently 1 everywhere). The fingerprint is the granular handle — bumps on every schema edit.

MechanismIdentifiesStable acrossUsed for
Idempotency keyThis invocation’s inputsRe-runs of the same inputsNo-op detection.
Schema fingerprintThe verb’s contract at PR timeSchema editsContract-version archaeology.

A re-run of the same verb with the same inputs but against an updated schema produces the same idempotency key (inputs unchanged) but a different fingerprint (schema changed).

  • Auditing old PRs. Looking at a 2024 PR with fingerprint e1d3c4f5a6b7? You can fetch the schema at that fingerprint from git history and see exactly what shape the verb expected then.
  • Spotting drift. A re-run that produces skipped_idempotent but with a different fingerprint than the existing PR’s body signals “the schema changed since the original PR was opened” — worth a glance to confirm the existing PR is still valid.
  • Migration triggers. When the fingerprint of a schema bumps, CI can grep open PRs for the old fingerprint and decide whether to close-and-reopen them.
import { createHash } from "node:crypto";
const text = readFileSync(`spec/verbs/${verb}.schema.json`, "utf8");
const fingerprint = createHash("sha256").update(text).digest("hex").slice(0, 12);

Computed on each apply. The 12-char prefix is enough collision resistance for the petrova-line scale (we’d need ~16 million distinct schemas before birthday-paradox risk becomes meaningful).