Events, Not Transactions: A Better Foundation for the Ledger
In 1494, Luca Pacioli wrote down the rules of double-entry bookkeeping, and business has run on debits and credits ever since. It is one of the most durable ideas in commerce: a way to compress every economic happening in the world into a pair of balanced numbers that always tie out. Every modern accounting system—from the general ledger in a Fortune 500 ERP to the books your bookkeeper keeps in QuickBooks—is a direct descendant of that idea. It works. We keep it.
But here is the thing about that compression: it is lossy.
When you record a sale as Cash $1,000 DR / Revenue $1,000 CR, you have a balanced, auditable, GAAP-compliant journal entry. What you no longer have, sitting in that entry, is who bought from you, what resource flowed to them, and why the policy said to book it this way. The journal entry is the accounting answer. The economic event was the question—and in a traditional ledger, the question is thrown away the moment the answer is written down.
RoboLedger inverts that. We record the economic event first, and we derive the double-entry transaction from it as a view. The debits and credits still exist, still balance, still satisfy your auditor. But underneath them, the event survives—and that changes what the books can do.
The Transaction Is a Consequence, Not a Cause
The cleanest way to say it: events explain the ledger; the general ledger is derived.
A sale, a payment, an asset disposal—those are the truths. They happened in the world. The general ledger is a consequence of those events, not a substitute for them. This isn't a critique of double-entry; it's a recognition of where double-entry sits in the causal chain. The debits and credits are downstream.
This framing isn't new. It's the REA model—Resources, Events, Agents—introduced by William McCarthy in 1982 and later formalized in ISO 15944-4. REA frames business events as a distinct, first-class layer above the GL, which is exactly the gap that double-entry-only systems leave. Charlie Hoffman's work on Data Centric Accounting describes the same gap in the same terms: the ledger is downstream of events.
And critically, deriving the GL from events is not a deviation from REA—it is REA. It's how the model actually manifests in the large systems that already implement it (Apex, SAP, NetSuite, Modern Treasury). The event-layer-plus-derived-GL shape is the textbook pattern. Most ledgers just don't expose the event layer to you. We do.
Here is the difference in one table:
| Traditional ledger | Event-driven ledger | |
|---|---|---|
| What you write | A balanced journal entry (you pick the accounts) | An economic event (who, what, why) |
| What's derived | Nothing—the entry is the record | The journal entry, computed by a handler |
| What's preserved | The accounting interpretation | The interpretation and the economic meaning |
| "Why is this number what it is?" | Trace to a balanced pair of accounts | Trace to the event and the policy that governed it |
That last row is the whole point.
Three Levels, Cleanly Separated
To make this work, RoboLedger uses three levels where most systems use one or two:
- Transaction — the business event: what happened in the real world.
- Entry — the accounting interpretation: a journal entry that must independently balance (Σ debits = Σ credits).
- LineItem — an individual debit or credit within an Entry.
The middle Entry layer is what separates two things that a two-level ledger conflates: the event and its accounting consequence. One business event can require several balancing journal entries—accruals, corrections, multi-fund allocation. One journal entry can stand alone, with no parent event, like a closing entry. Keeping these distinct is what lets the same model handle a clean QuickBooks import (where one entry maps 1:1 to one transaction) and a messy month-end accrual (where one event spawns several entries) without special-casing either.
Above all three sits the event, carrying the economic meaning. Every posted entry points back, through a triggered_by_event_id link, to the event that produced it. That back-link is the thread you pull when you need to explain a number.
A Worked Example: Disposing of an Asset
Consider what it takes to dispose of a piece of equipment partway through its life.
In a traditional ledger, this is your problem to solve. You have to know the asset's original cost, look up its accumulated depreciation, compute the net book value, figure the gain or loss against the sale proceeds, and then hand-construct a journal entry that touches four or five accounts—and balances. Get the accumulated-depreciation number wrong and the entry still balances; it's just wrong. The ledger has no idea what you meant. It only knows the debits equal the credits.
In RoboLedger, you record one event:
Event: asset_disposed (occurred_at = 2026-03-15)
metadata: { schedule_id, proceeds = $3,000,
proceeds_element, gain_loss_element }
That's the whole write surface. You declared what happened—this asset was disposed of, for $3,000, on this date. A handler then fires atomically and does the accounting for you:
Accumulated depreciation (from the schedule) = $2,500
Asset cost = $10,000
Net book value = 10,000 − 2,500 = $7,500
Gain / (Loss) = 3,000 − 7,500 = ($4,500) loss
Disposal entry:
Accumulated Depreciation $2,500 DR
Cash $3,000 DR
Loss on Disposal $4,500 DR
Computer Equipment $10,000 CR
The handler pulls the accumulated depreciation from the asset's own schedule, computes the net book value and the loss, drafts the balanced entry, voids the future depreciation events that will never happen now, and links every generated transaction back to the disposal event. You didn't tell it which accounts to touch. You told it what occurred in the world, and the GL fell out.
This inverts the original footgun, where the caller had to know the accounts before they could write anything. The event is the input; the journal entry is the output. And because the event is preserved, the entry is explainable: six months later, an auditor (or an AI agent) can ask "why is there a $4,500 loss on the income statement?" and walk the link back to the disposal event, the $3,000 in proceeds, and the depreciation schedule that set the book value. In a transaction-first ledger, that same question dead-ends at a balanced pair of accounts.
What "Underneath" Buys You
The phrase is "events, underneath transactions"—not "transactions are obsolete." The double-entry layer is still there, doing exactly what it has always done. But putting the event underneath it pays off in a few specific ways.
Adapters and AI write events, not journal entries. There is no raw "create journal entry" surface for an integration to fumble. A QuickBooks sync, a bank-feed import, or an AI operator all send one event-block write. The system validates the event, finds the matching handler, generates the transaction preview, and posts—all in one atomic operation. The caller never has to know debits from credits. It just reports what happened.
Recording a manual entry is itself an event. We briefly considered keeping a separate "manual journal entry" surface alongside the event layer—a "real events" path and an "adjustments" path. That split turned out to be false. Recording a journal entry is a real-world act: someone decided to book something. So manual GL writes flow through the event layer too, as a journal_entry_recorded event. The rule is simple and total: if it writes to the GL, it flows through an event. Nothing reaches the books except by way of something that happened.
Receivables and payables fall out of the event store directly. Because each event can link to the event it settles, AR and AP are just a traversal—no separate subledger to reconcile:
AR for a customer = Σ(invoice.amount)
− Σ(payment.amount that discharges that invoice)
Partial payments work for free as multiple settlement links. This is a tiny schema primitive—two nullable links on each event—placed exactly where REA's full duality algebra would go. It buys most of the value without the formal machinery.
The books become AI-operable. This is the payoff that matters most for where accounting is going. An AI agent operating a transaction-first ledger is reverse-engineering intent from balanced numbers—guessing at the why from the what. An agent operating an event-first ledger reads the event: the counterparty, the resource, the action, the policy. When the meaning is preserved in the record instead of compressed out of it, the agent can answer "why is this number what it is?" by tracing causation, not by pattern-matching account names. Explainability isn't a feature we bolted on; it's a property of recording the event in the first place.
What Stays an Event—And What Doesn't
A discipline keeps this honest, and it's worth stating because it's the part that's easy to get wrong: events explain; workflows manage state.
Closing a period is not an event. Your customers didn't change their behavior on March 31st. Closing the books is a procedural action—"I'm done reviewing March; lock it." So close-period, reopen-period, and similar operations are workflows, not events. They don't get rows in the economic-event store, because nothing happened in the world; something happened to your books. (They keep their own separate audit trail, so nothing is lost.)
This boundary is what keeps the event store meaningful. It stays a record of what happened in the business—not a dumping ground for every state change anyone made to the system. The moment you let "I closed the period" sit next to "the customer paid the invoice," you've diluted both. Getting this line right is what makes the event layer trustworthy enough to derive everything else from.
| Event | Workflow | |
|---|---|---|
| Answers | "What happened in the business?" | "What did the operator do to the books?" |
| Examples | Sale, payment, asset disposal, accrual | Close period, reopen period, materialize |
| Lives in | The economic-event store | A separate operational log |
| Derives the GL? | Yes—handlers produce entries | No—it manages state |
The Same Idea, All the Way Up
There's a longer arc here. Once the economic event is a first-class object, it becomes the seam for everything that sits above accounting too—the intents, commitments, and processes that a coordination layer like Valueflows models. That layer plans and coordinates economic activity; the accounting derivation sits below it. Most systems that try to model coordinated economic activity hand-wave the accounting derivation as "a computer program, run on request." That program is the ledger. We built the half they punt on—and because the event sits at the seam, the same substrate that powers RoboLedger powers whatever comes next.
That's the bet, stated plainly: the economic event is the right primitive to build a financial platform on, because it's the thing every layer—the books below it and the coordination above it—actually shares.
Try It
Double-entry bookkeeping was a brilliant compression of economic reality, and we kept every bit of it. The balance sheet still balances. The auditor still gets their journal entries. What we added back is the thing the compression threw away: the economic event underneath, carrying the who, the what, and the why all the way through to the financial statements.
The result is a ledger you can actually ask questions of—one where "why is this number what it is?" has an answer you can trace, not just a balanced pair of accounts.
RoboSystems is open-source and self-hostable, and RoboLedger runs on top of it. If you want to see what a ledger looks like when the event comes first and the journal entry is derived, start at robosystems.ai. Record an event. Watch the books fall out. Then ask why.
Joey French
Contributing to the future of graph databases and AI-powered business intelligence.
Ready to Build Your Knowledge Graph?
Experience the power of graph databases with RoboSystems.
Get Started on GitHubMore from RoboSystems Blog
Financial Reports as DataBooks: One Artifact for Humans, Machines, and LLMs
Jun 19, 2026
A published financial report should be something you can read with your eyes, query with SPARQL, and validate with SHACL—without loading a single specialized tool. So we built a proof of concept: our reports, rendered as DataBooks.
The Open SEC Data Repository: Every Filing as a Queryable Graph
Jun 19, 2026
Every public company's financials are already public—and almost nobody can actually use them. Here's the open, queryable graph we built on top of SEC XBRL, and what it unlocks.
From Numbers to Narratives: Bridging Structured Data and Document Search
Mar 20, 2026
Financial analysis needs both the numbers and the story behind them. We built a platform that bridges structured XBRL facts in a knowledge graph with full-text search across SEC filing narratives—and lets AI chain both together.