Expand description
The persistent spend journal that holds R-29’s caps (spec 012, 3.8): a shared cost ledger that outlives a run (spec 003, 3.5.2), kept by the host outside any repository.
Two budgets: testing, USD 10 in total (10,000,000,000 units of one
nano-USD, never reset; A-75 raised it from R-29’s USD 5), and production, USD 25 per UTC calendar month
(25,000,000,000 units per month). Before dispatch the adapter reserves
its estimate; the journal refuses (a hard stop, nothing is sent) when
observed + estimated + liability + outstanding reservations + this
reservation would pass the cap. After the answer the reservation is
settled with the charge; an unknown charge keeps the reservation as
liability until a later observed charge reconciles it.
Format. Append-only JSON lines, each written with one write and
flushed to disk with fsync before the call returns. The first line is
a header naming the schema, the budget and the cap; every later line is
one of reserve, settle, reconcile or release, keyed by a
reservation sequence number. The state is the replay of the lines. A
reservation is durable before its request can be sent.
Header migration (A-75). A testing journal whose header names the
superseded cap (SUPERSEDED_TESTING_CAP_UNITS) is opened under the
lock and its header is replaced by the current one: a copy holding the
new header followed by every later byte unchanged is written beside the
journal, fsynced and renamed over it, and the directory is fsynced.
A crash leaves either the old file or the new one, never a mix. Entries,
sequence numbers and unsettled reservations are untouched. Any other
header that differs from the expected one is still refused.
Crash safety. A final line without its newline was never completed: it is cut off at open. Since a reservation is fsynced before sending, a cut reservation was never sent; a cut settlement leaves its reservation outstanding. A reservation still outstanding when the journal is opened (its process ended before settling) counts as liability: its request may have been sent. Every failure therefore errs toward counting more.
One writer. A lock file beside the journal (<journal>.lock,
created exclusively) keeps a second process out. A process that dies
leaves it behind; the host removes it after checking that no process
uses the journal. Within a process, clones share one journal.
Structs§
- Billing
Settlement - A provider billing line settling one previously unknown attempt. This is supplied by the host from the provider record, never inferred from a timeout, a missing charge, or a late adapter response.
- Reservation
- A reservation made before dispatch.
- RunSpend
- The run’s settled charges and exposure, across all periods.
- SetClock
- A clock that reads what it was set to.
- Spend
Journal - A persistent spend journal. Clones share it.
- Spend
Summary - The journal’s totals for one period, in units.
- System
Clock - The system clock.
- Unresolved
- Why a production fact, binding or billing settlement is unresolved
(spec 022);
productionre-exports it.
Enums§
- Budget
Kind - Which of R-29’s caps a journal holds.
- Journal
Error - Why a journal could not be opened.
- Spend
Refusal - Why a reservation was refused. Nothing may be sent.
Constants§
- JOURNAL_
SCHEMA - PRODUCTION_
CAP_ UNITS - R-29: USD 25 per calendar month for production, in nano-USD.
- SUPERSEDED_
TESTING_ CAP_ UNITS - R-29’s original testing cap, USD 5, in nano-USD. A testing journal whose
header names it is migrated to
TESTING_CAP_UNITSwhen opened. - TESTING_
CAP_ UNITS - R-29 as raised by A-75 (2026-11-03): USD 10 in total for testing, in nano-USD.
Traits§
- Spend
Clock - The time the journal reads to choose a period. Injected, so tests can cross a month boundary.
Functions§
- utc_
month YYYY-MMof a Unix time in milliseconds, in UTC.