Two years after a loan is originated, someone asks: what exactly were the terms of the product this loan was made under? Who approved them, and when did they take effect? In most lending companies the honest answer is archaeology — a configuration table with an updated_at column, a deployment log, an email thread, a spreadsheet named final_v3. The information existed at some point. As evidence, it is worthless.
The question is not hypothetical. It arrives as a borrower dispute, an audit, or a supervisory review, and the quality of the answer was fixed long before anyone asked — by how the catalog stores change. We built the Capcells catalog so the answer is a query. Three properties make that work.
Versions are values
In Workspace, editing a product’s terms never updates anything. It writes a new, immutable version. Going live is a separate act: a pointer moves to the version that governs new business. The old versions stay exactly as they were — not archived, not overwritten, just permanently what they always said.
That sounds like a storage detail. It is a change in what a product is. A version is a value, like the number 7: it cannot be edited, only referenced. Every simulation result, every disclosure, every downstream record traces to the exact version it came from — and the reference will mean the same thing in ten years, because the thing it points to cannot drift.
A signer and an effective date
Immutability answers what. Evidence also needs who and since when. Every product version and every market-rule version carries a recorded human signer and an effective date. The agent can flag a weak product and propose a concrete change, but a person reviews and approves before any version is written, and every approval is logged. There is no path into the catalog that bypasses a named human decision.
This is deliberately un-clever. When a regulator asks who decided, the system should not answer with the name of a service account.
A chain, not a log
An append-only table protects you from careless updates. It does not protect you from a deliberate one — a row quietly rewritten by someone with database access still looks like an append-only table afterward. So catalog changes, agent actions, and ledger entries each append to a hash-chained log: every entry carries the hash of the one before it. Rewrite any historical entry and every hash after it stops matching. The history does not just record — it can prove it has not been altered, and answer who decided, when, and on what basis.
A loan binds to its version
All of the above would still be bookkeeping if live loans floated on top of a mutable catalog. They do not. When the Engine originates a loan, it resolves the exact product version in force, re-runs the same coherence checks Workspace ran at definition, and binds the loan to that version permanently. Edit the product tomorrow; the loan’s math does not move. Every credit decision, approved or declined, is recorded with the exact signed parameter versions behind it.
The calculation ledger takes the same stance. Every accrual, allocation, and penalty is appended, never mutated; a correction is a reversing entry that states what changed and why — not an edit that states nothing.
What evidence is
- Complete — the history is append-only, so the absence of a record means the event never happened.
- Attributed — every change carries a recorded human signer and an effective date.
- Intact — the hash chain proves the record has not been rewritten.
A catalog with those three properties changes the character of a bad afternoon. “What were the terms, who approved them, and what has the loan actually done” stops being a reconstruction project and becomes a query: same version, same rules, same numbers, on demand.