LatentAxis
← Work

Financial Document Intelligence

Axiom

A multi-tenant service that reads financial documents with a fine-tuned model, learns from corrections, and pushes structured data into accounting systems.

Year
2025
Stack
FastAPI · LayoutLM (fine-tuned) · Claude · SQLite · QuickBooks · Xero · APScheduler

The problem

Financial documents are a parsing nightmare: every bank, vendor, and accounting package emits its own statement and invoice format, and the people who have to reconcile them do it by hand. A general LLM can read one document well, but doing it at volume, accurately, cheaply, and with an audit trail, is an engineering problem, not a prompt.

Axiom ingests statements and invoices from Google Drive, OneDrive, or direct upload; extracts and classifies the transactions; and pushes structured results back out to QuickBooks, Xero, or a webhook. The interesting parts are how it stays cheap, how it gets better over time, and how it stays auditable.

The document pipeline

Ingest Drive · OneDrive · upload
OCR Tesseract
Parse PDF · CSV · bank-specific
LayoutLM fine-tuned weights
Classify enrich · dedup · reconcile
Push QuickBooks · Xero · webhook
Fig. 1 · Ingest to structured output

Decisions worth surfacing

Confidence-gated dual-model serving. A locally fine-tuned LayoutLM model handles extraction first. It’s fast and free per call. Every prediction carries a confidence score; below a configurable threshold, the row falls back to Claude for a second opinion. Each transaction records which path it took, so you can watch whether the local model is regressing and whether retraining is actually helping, rather than paying for a frontier model on every line item.

Online retraining with an atomic version flip. User corrections accumulate in a corrections table. Once enough pile up, an APScheduler job trains a new model into its own models/weights/vN/ directory and writes a new row to a model_registry table. Serving behaviour changes only when a single is_active flag flips to the new row. No file mutation, no service restart, no warmup hit, and rollback is one flag away.

Corrections user edits
Trainer APScheduler
Weights vN model_registry row
Atomic flip is_active = 1
Fig. 2 · The learning loop

Two databases, split by concern. Authentication and tenant config live in one SQLite database; the domain data (documents, transactions, anomalies, the model registry) lives in another. The auth DB is small and stable; the data DB is the one that grows. Splitting them means they back up and restore on independent cadences, and a schema migration to one never risks the other.

Three key types with scope hints. Each tenant has a dashboard key (UI), a service key (server-to-server, e.g. a Drive watcher writing back on the client’s behalf), and a legacy API key for backward compatibility. An optional X-Key-Scope header lets a client narrow exactly which credential is being checked, defending against key-confusion bugs and keeping audit trails clean.

Idempotent by construction. Webhook ingestion is logged with status code and latency on every attempt, and a uniqueness constraint on (config_id, file_id) guarantees the same Drive file can’t be processed twice. That’s the kind of guarantee you want before you let an automated system write into someone’s books.

Note

Axiom was built as a complete, deployable platform; the case study above describes the system architecture rather than client deployments. Customer-identifying details are intentionally omitted.