Receipts: what a closed and an unclosed file prove
Not available yet. The receipt tools are not in the free download and their source is not published, so no install can write or check a receipt today. This page says what a receipt will prove once they ship.
A receipt is a signed line written for each tool call a supervised agent makes: which tool, with what input, what it returned, and when. Receipts are written by a sidecar that watches the agent's session from outside it, never by the agent itself, so an agent cannot forge, hide or backdate its own.
Where they come from. The receipt tools, din-receipt-emit and din-receipt-verify, are part of the open-source record producer and are not in the free download. The capture plugin's own records are marked logged, not receipted: see The honesty grading.
Writing receipts
tail -f -n +1 --pid=$AGENT_PID run/session.jsonl \
| RECEIPT_HMAC_KEY=... RECEIPTS_OUT=run/receipts.jsonl din-receipt-emit
RECEIPT_HMAC_KEY is required (the emitter exits 2 without it). Give the key to the emitter only, never to the agent. When the session ends the emitter writes a signed close record, receipts.close (mode 0600), beside the receipts (RECEIPTS_CLOSE moves it).
Checking receipts
RECEIPT_HMAC_KEY=<key> din-receipt-verify [--strict] [--allow-gaps] [--allow-empty] [--require-close] [--close <receipts.close>] <receipts.jsonl>
| Result | Exit | What it means |
|---|---|---|
OK <n> | 0 | Every receipt verifies, and the file matches its close record: nothing was cut from the end, torn, reordered, duplicated or appended. |
OK-UNCLOSED <n> | 3 | Every receipt verifies, but there is no close record, so the end of the file is not protected: lines cut from the tail would not show. Every file written before close records existed reads this way. |
TAMPERED ... then FAILED ... | 1 | A receipt or the close record does not verify, or the file does not match its close record. |
FAILED ... | 1 | A gap in the sequence, a broken chain, or an empty file. |
| 2 | A usage error, RECEIPT_HMAC_KEY unset, or a file that cannot be read. |
Exit 3 is not success. A script that checks $? -eq 0 treats an unclosed file as not proven, which is right. To make an unclosed file a plain failure, pass --require-close (it then exits 1).
The options
--require-close: no close record is a failure (exit 1), notOK-UNCLOSED.--allow-gaps: a gap or a broken chain is a warning, not a failure. A file with a close record still fails if its tail was cut.--allow-empty: accept an empty file.--strict: every receipt must carryprev_sig, the link to the one before it.--close FILE: the close record, when it is not beside the receipts.