Back to Beads

bd contract corpus — producer catalog

cmd/bd/protocol/CATALOG.md

1.2.13.5 KB
Original Source

bd contract corpus — producer catalog

This package is the producer half of the Beads ↔ consumer cross-version contract-test system. It pins the bd --json wire surface that a downstream consumer's decoder consumes, by generating a canonicalized golden-JSON corpus under testdata/corpus/ and failing CI on any unreviewed change to it.

A downstream consumer vendors this corpus and replays it against its own decoder, so a bd release can never silently change a wire shape the consumer parses.

How it works

  • corpus.go — the deterministic command plan, the canonicalizer (timestamps → <TS>, object arrays stable-sorted, keys sorted, 2-space indent), and the provenance manifest.
  • corpus_test.goTestCorpusGolden runs the plan against a live bd (built from source, Dolt-backed) in both flat and BD_JSON_ENVELOPE=1 variants, canonicalizes, and byte-compares against the committed corpus. A diff is a hard failure (make corpus-regen to update); a Dolt-boot failure is an infra skip, never a silent pass.
  • canonicalize_test.go — unit tests for the canonicalizer plus TestCorpusDoubleRunByteIdentical, the determinism backstop that generates the corpus twice and asserts byte-identity.

Regenerate after any deliberate wire change: make corpus-regen, review the diff, and bump JSONSchemaVersion (cmd/bd/output.go) — the schema_version field in every blob is the coordination canary a downstream consumer keys its pinned-decoder migration off.

Coverage

Blob (flat + envelope)bd commandContract domain
create_root, create_dep, create_closed, create_deletedbd create … --jsonjson-output-shapes (object)
showbd show <id> --jsonjson-output-shapes (array-of-one), dependency shape
updatebd update … --jsonjson-output-shapes (mutation array), label add + metadata coercion (phase → string)
closebd close --reason … --jsonclose semantics (close_reason, closed_at)
reopenbd reopen … --jsonreopen semantics (status back to open)
listbd list --all --jsonjson-output-shapes (array / list envelope)
readybd ready --jsonready-projection-semantics
dep_add, dep_listbd dep add/list --jsonjson-output-shapes (dependency)
dep_removebd dep remove … --jsondependency-edge removal confirmation
deletebd delete --force … --jsondelete confirmation shape
countbd count --jsonjson-output-shapes (scalar)
versionbd version --jsonversion-compat, the schema_version canary
errorbd show <missing> --jsonexit-codes-and-errors ({error, schema_version})

Known gaps (tracked, not silent)

  • bd sql is not supported in embedded mode (this harness's mode), so it is not in the corpus. A downstream consumer's ready-projection enrichment depends on bd sql against a managed Dolt server; covering it needs a server-mode generation path.
  • The show blob pins the count-only default payload (comment_count, dependent_count); the opt-in --include-comments / --include-dependents shapes are not in the corpus. They are covered at the CLI level by the preservation and round-trip tests, not byte-pinned for a consumer.
  • The error blob pins the not-found envelope; other error classifiers (claim-conflict, silent-fallback auto-import, bd sql unsupported) are plain-text on stderr and belong in a separate error-string fixture set.