It cannot certify, sign off or file your books — the state does not exist to write
Asking to mark a handoff certified, signed_off, filed or finalised is refused with a 403 and a redirect to a qualified accountant, and the refusal itself is audited. This is not a permission check on an enum member that happens to be missing — the words are matched explicitly so the caller is told what the product does and does not do, rather than receiving a validation error about an unrecognised string.
A journal entry cannot be edited or deleted — only corrected by a new one
There is no PATCH or DELETE anywhere on the ledger. The only correction route posts a new entry that points back at the original, generated as an exact reversal from the original's own lines rather than hand-typed, because a hand-keyed reversal is the one correction that could itself be wrong.
A closed period refuses every write
Closing a period freezes it: posting an entry, correcting one, or importing a statement line into a closed period's dates is refused with a 409 naming the reopen route and asking for a stated reason. Reopening is a separate act, not a flag on the close route, because it is the exception an accountant most needs to see.
It will not post an unconfirmed document to the books
A captured document sits in needs_review however good its extracted figures look. Only a person confirming the values match the original moves it to confirmed, and posting refuses anything else with a 409 naming the confirmation route — the same gate an OCR-extracted draft would have to pass through.
It will not guess a category — no matching rule returns nothing, not a default
A category suggestion comes only from a rule the workspace itself wrote. When none matches, the response says so explicitly rather than defaulting to a catch-all category, because a silent default is accepted by a busy owner and quietly becomes the largest line in their accounts.
Every trial balance, ledger listing and handoff carries an 'Unaudited' label
The label travels with the data itself — inside the JSON, not only in a UI badge — so a trial balance pasted into an email or exported still says what it is: a working document for a bookkeeper, not a financial statement.