Skip to content

ADR-011: vectorflow-cloud disposition ledger and disposition vocabulary

Source of truth: docs/adr/011-vectorflow-cloud-disposition-ledger.md (synced at build time — edit the original, not this copy). Status: Accepted (2026-08-11)

Decision owner: Danny

Issues: #203, #451

Amended by ADR-016 §36: the ledger scripts and their verify.yml job are retired. conformance/disposition-ledger-v1.json and conformance/commit-inventory-v1.json stay in the tree as the record, and archiving vectorflow-cloud itself is an owner action.

veltrosecurity/vectorflow-cloud is the retired synchronized-superset offering: ADR-010 §8 quarantines it as historical/provenance evidence and forbids reviving it as a source tree or synchronized superset. Epic #203 requires that no code movement, deletion, or archival happens until there is a machine-readable record of what exists and what is to happen to it, and that record does not exist.

This ledger is the first child: an inventory and evidence record only. It moves, deletes, and archives nothing.

1. A machine-readable disposition ledger is the record

Section titled “1. A machine-readable disposition ledger is the record”

scripts/disposition_ledger.py walks a pinned snapshot of vectorflow-cloud’s default branch (fetched fresh, with the commit sha recorded in the output, never a stale local checkout), classifies every path, and writes conformance/disposition-ledger-v1.json as the reviewed, checked-in ledger. The ledger records the pinned sha, the full path->disposition resolution, every unresolved reason, the prisma models, and the tracked env gates. The scripts/test_disposition_ledger.py gate and the verify.yml config job fail closed on any unclassified path and on any drift (a live vectorflow-cloud head that no longer matches the recorded pin), so the record cannot silently go stale as the source repository changes.

2. There are exactly six dispositions, taken verbatim from #203

Section titled “2. There are exactly six dispositions, taken verbatim from #203”

Every path, model, migration, provider, workflow, and infrastructure asset receives exactly one:

  1. port-public-fixed-realm — reusable open-source security/identity primitive proven free of Organization/MSSP behavior; reimplemented in the public fixed realm. Not proven => not classified here.
  2. port-vectorflow-product — Team/Environment, product data, product isolation, quotas/usage, and product operations; the capability lives in the canonical public VectorFlow product. Duplicated bytes are never canonical.
  3. generalize-public-contract — bounded conformance/security tests and wire contracts, generalized into a reviewed public contract.
  4. archive-reference — hosted signup, billing, operator, Organization/MSSP workflows, historical architecture, threat models, provenance, migrations, and incident/recovery evidence; retained as a quarantined reference.
  5. retire — only after proving no live dependency and satisfying retention and deletion obligations. This ledger retires nothing.
  6. unresolved — explicit product, legal, licensing, security, or operational decision required. Must carry a reason.

There is no port-commercial class while Organization/MSSP is deferred (#57).

3. unresolved is first-class and must carry a reason

Section titled “3. unresolved is first-class and must carry a reason”

A path may not silently default into a bucket. Every unresolved entry records why: e.g. the licensing files (LICENSE-CLOUD.md, OPEN-CORE.md, CLA.md) are unresolved pending the separate licensing-resolution decision (#203), and the SCIM/SAML identity surfaces are unresolved pending an org-free proof and the identity cutover decision (ADR-010 §3, #130).

The ledger commits only to classification and evidence. It does not authorize movement, deletion, archival, redeployment, credential or cloud-resource cleanup, or any external-state change; each of those remains a separately approved child of #203 behind the epic’s evidence gate.

  • A reviewer can answer “what is this path and what is to happen to it” today, for all 2099 paths of the pinned snapshot, without joining artifacts by eye.
  • The later children — licensing resolution, unique-commit inventory, deployment and external-state inventory, and the archival gate — all start from a total, reproducible record.
  • Maintenance cost: any advance of vectorflow-cloud (new path or new sha) fails the gate until the ledger is regenerated and re-reviewed.
  • Candidate port-public-fixed-realm security/identity primitives are recorded as unresolved rather than claimed; reimplementation in the canonical product is a later, separately gated step.
  • The ledger and this ADR are registered as reviewed surface entries in the public-capability inventory, and the disposition vocabulary is exempted in the composition-abuse corpus, so the existing no-growth gates stay green as this program proceeds.
  1. A per-path hand-authored JSON with no generator. Rejected: it cannot fail closed on a changing tree and would drift the moment the source moved.
  2. Walking a developer checkout instead of a fresh pinned snapshot. Rejected (issue risk note): a stale tree would classify a world that no longer exists; the ledger pins and records the sha instead.
  3. Silently defaulting unmatched paths into a disposition. Rejected: the issue names this the failure mode; unmatched paths fail closed instead.
  4. Adding a port-commercial disposition. Rejected: the Organization/MSSP concept is deferred, so no class exists to receive it (epic #203).