Home › Use Cases › Reconcile one book's income postings against what the terms and the position entitle it to
Use caseUC0402
🧪 Use-case kit · runnable

Reconcile one book's income postings against what the terms and the position entitle it to

A small, forkable project that does one job end to end. Run once for real, and every figure on these pages captured from that run.

The business caseThe problem this solves

A book's income is decided by three records that were never written to agree: what the issuer announced, what the book actually held at the record date, and what somebody posted. An announcement gets revised by a supplementary notice that arrives as a sentence. Units on loan over the record date look exactly like units held. A reversal and the posting it reverses look like two payments. A duplicate and a mis-rate are the same arithmetic and two different problems. The reconciliation most books run is a column comparison, and on this corpus the book's own answer is wrong on 30 of 62 events. Opening one event, reading the announcement against the terms the book captured, checking the correspondence for a revision or a stock loan that moves the entitlement, working out which postings belong to the event and which belong to another, recomputing the entitlement at the right rate on the right quantity, and deciding whether an unposted event is late or simply not due yet.

Audience

The asset-servicing desk at a manager or a fund administrator working a period's income variances, and the operations analyst behind it. Whoever reads the output is deciding which events go back to the custodian, which go to the registrar and which close. Every number on these pages came from one real run of this code, not from a vendor page.

The inputThe actual income event file

The corpus is 62 income event file, 0.13 MB (txt 62). It is generated because it has to be. A real income reconciliation is a book's own holdings, a custodian's correspondence and an issuer's announcements for a named fund, and the exact shapes this kit is about — a rate revised by a supplementary notice, units on loan across a record date, a duplicate posting nobody reversed — are the ones a manager would least want published. Generating it also makes the key DERIVABLE: each event is built as a structure and IPR-2026 is applied to that same structure, so there is no second place the answer lives and a corpus change cannot leave a stale label behind.

The corpus

  • The 62 income event filegenerated from a fixed seed, so no real record, person or institution appears in it.
  • Where each came fromdata/SOURCES.md states where every byte came from AND what the generator costs the measurement. Every book, security and event is an invented code and name, and THERE ARE NO SECURITY IDENTIFIERS IN THIS CORPUS — no CUSIP, no ISIN, no SEDOL, no ticker — because a generated identifier that collided with a real instrument would be the one thing on this page that was not invented. THERE ARE NO PEOPLE IN IT EITHER: correspondence is signed Custodian, Registrar or Operations. evals/check_labels.py sweeps all 62 files for a person-shaped name and an honorific on every run and reports 0.

Swap this folder for your own material and the kit is pointed at your income event file. That is the whole change — there is no database to migrate.

One income event file, as the model receives itINC-0001.txt · 1 of 62
==============================================================================
INCOME POSTING RECONCILIATION -- ONE BOOK, ONE INCOME EVENT
==============================================================================
FILE           INC-0001
BOOK           BK-7741  Meridian Balanced
SECURITY       SEC-30214  Calderfield Utilities Ordinary
EVENT          EVT-40000  CASH DIVIDEND
PERIOD         2026-04-01 to 2026-06-30
AS-AT          2026-06-30
POSTING WINDOW 2 business days after the pay date
TOLERANCE      2.00
CURRENCY       USD

-- ANNOUNCED TERMS -----------------------------------------------------------
TERM      ANNOUNCED   EX DATE     RECORD DATE  PAY DATE    RATE/UNIT  WHT%   SOURCE
ANN-0200  2026-05-22  2026-06-08  2026-06-09   2026-06-24  0.420000   15.00  issuer announcement, primary feed

-- POSITION LEDGER AT THE RECORD DATE ----------------------------------------
LOT       SOURCE                       QUANTITY  TRADE DATE  SETTLE DATE  STATUS
LOT-4400  opening position                3,200  --          --           SETTLED
LOT-4401  purchase                          800  2026-05-27  2026-05-29   SETTLED
POSITION AS BOOKED AT RECORD DATE               4,000

-- INCOME POSTINGS ON THE BOOK IN THE PERIOD ---------------------------------
POSTING     POSTED      TYPE      EVENT REF   GROSS           WHT           NET
POST-11001  2026-06-24  INCOME    EVT-40000   1,680.00        252.00        1,428.00
POST-11009  2026-06-29  INCOME    EVT-39000   1,455.00        218.25        1,236.75

-- CUSTODIAN AND ISSUER CORRESPONDENCE ---------------------------------------
CORR-0030  2026-06-23  Custodian: the payment for this event reached the cash account and has been advised.

Abridged — the file continues.

The outcomeWhat a good result looks like

One income event in, one row out: the governing rate, the entitled quantity, the postings that belong, the row that establishes the figures quoted verbatim, the variance recomputed in code, and one of five IPR-2026 verdicts. It posts nothing, files nothing, states no deadline and names no person.

And when it cannot

And what it does when it cannot. On the scored run 62 of 62 replies parsed, nothing stopped at the ceiling and no call failed. Where it is wrong it is almost always wrong by citing MORE than the key holds — 15 events — and never by missing a row the key holds, which is 0 of 62. On 5 events it took an income posting carrying no event reference at all, and on 2 of those that turned MISSING into AGREED, which is the worst direction this kit can be wrong in. The station cannot notice either: it re-derives faithfully from whatever reading it is handed and returns a verdict with full confidence, and the arm's own confidence does not separate them — median 0.95 on the events it got whole and median 0.95 on the events it got wrong.

Where it fitsWhat did work

Every line below is a measured result from this kit's own runs, with the figure that supports it. The headline above is not softened by any of them.

  • Your custodian sends revised rates as a CORRECTED ROW in the terms feed, and your stock-loan positions are a column on the position file — the free modal floor, and do not buy a call at all
    45 of 62 events for $0.00, and it BEATS the paid call on this corpus's five-field headline. Pending lots, reversals, duplicates, a withholding rate that does not match the terms row and an event nothing was posted for are all decidable from columns and dates.
  • Your revised rates and your stock loans arrive as SENTENCES — a supplementary notice, a custodian advice, a registrar's line — the paid call, and read the entitlement number rather than the five-field one
    The modal floor gets 0 of 17 on the events where a sentence decides. The paid call gets 15 — 15 discordant pairs its way against 1, p = 0.000519.
  • You want the output never to state a filing deadline or name a person — either arm, and keep src/refusal.py
    0 deadlines asserted, 0 person-shaped names, 0 blame assertions, 0 proposed actions and 0 finality claims on every committed arm AND on all 20 attacked events, including the 5 handed a clause asserting a 90-day filing window as fact.

And where nothing here is good enough:

  • You need the evidence row for an auditor and an exact set matters — neither yet — or accept recall rather than exactness
    The paid arm cited every row the key holds on 62 of 62 events and cited EXTRA rows on 15. If your reviewer can drop an extra row, this is a 59-of-62 product; if the set must be exact, it is 47.
  • Somebody can write a correspondence line into the file you send — neither, until you have a control on the reading
    A FALSE supplementary notice took 5 of 5 attacked events. The kit believes a revision notice, which is exactly what makes it worth buying and exactly what makes it attackable.
  • Your posting window has to honour a market or currency holiday — neither, until you add a calendar
    src/money.py::business_days skips Saturday and Sunday and nothing else, so an event over a public holiday reads as past its window when it is not.

At a glanceHow the whole thing runs

50%all five correct pct
1,998 msp50, end to end
$0.00per 1,000 income event file · the fast tier

Run once, for real, on 2026-09-12. Every figure on these pages was captured from that run — nothing is written from intent.

14 steps, grouped by the question that sends you to them rather than by build order. Each tile carries the one figure that step is about, and opens the page behind it.

Should you use this?What you bring, where it stops, and when not to use it

Before you commit an afternoon to this, these are the answers that decide it. Each one is rendered from the record it lives in — and links the page that holds it in full.

What do I have to bring?Replace data/corpus/*.txt with your own income event files in the same shape and data/books.json with your own posting windows, tolerances and withholding rates. ⚠︎ WHAT STOPS BEING TRUE THE MOMENT YOU DO. Corpus lens →
When is this the wrong choice?Avoid: Paying per event for arithmetic you already have. That is the case against the best-fitting scenario (“Your custodian sends revised rates as a CORRECTED ROW in the terms feed, and your stock-loan positions are a column on the position file”). 6 scenarios scored in all, each with its own. Eval lens →
Where does it stop working?A book whose REVISED RATES arrive as a second row in the terms table rather than as a sentence. The whole margin over free code is that a revision is prose; given a column, the free floor wins and the call is not worth buying. 9 recorded failure modes, each from a run rather than a guess. Corpus lens →
What was never verified?NO SECOND SCORED RUN. One was fired, so the run-to-run spread on this corpus is unknown and no confidence interval is claimed anywhere on this page. 10 items this kit says it could not check. Eval lens →
Can I run this on a model I control?Yes — any OpenAI-compatible endpoint, including one on your own hardware. The shipped adapter takes its host from BASE_URL and its model from MODEL, so nothing in src/ changes. The published figures come from 1 model on the fast tier, one provider, one key. Prompt lens →
And if it fits — what do I stand up?6 artifacts with a stated home and a stated egress, and 3 decisions each with what you provision past its ceiling — plus what was not measured. That is the next page, not this one. step 14 — Run it in your environment →

Not asked of this kit — 2 questions: clone (a fresh clone of this kit runs with nothing fetched); judge (nothing here is graded by a model).

Last verified 2026-09-12 — r001-income-posting. Every figure on these pages was captured from that run.

Run itHow this reaches your data

Every result on this page was produced by pure code over checked-in files, with no API key — which is why you can read the numbers before anyone spends anything.

Run this on your own data

  • The pipeline, its eval harness and the runs behind every numberdeployed inside your environment, on your own model endpoints, against your own documents.
  • The corpus above is the shape, not the limitit is a folder swap, and there is no database to migrate.

Talk to us →

Checked before this shipped — A clean checkout with no key configured renders the whole board, all three free floors and every committed run. python3 tools/build_corpus.py --check rebuilds all 62 files byte-identically (verified under three PYTHONHASHSEEDs), python3 -m evals.check_labels re-derives the key independently at 0 disagreements, and python3 -m evals.run --run-id b000-income-posting-modal --floor modal scores the best free arm. No pip install: the kit is standard library only.

A living map of modern AI — kept current every morning