Accounts payable, automated. With a leash.

The AI that pays your invoices, and knows exactly when not to.

AP Autopilot extracts, matches, and risk-scores every invoice automatically. But the decision to move money never touches a language model. It passes through a deterministic policy engine, and every step lands in a hash-chained ledger your controller can replay months later.

Measured, not claimed
0%
false-approve rate
26-invoice adversarial test corpus: duplicates, mismatched POs, fraud patterns
0.5s
avg. autonomous resolution
submission to paid-and-reconciled, clean invoices
94.2%
field extraction accuracy
including deliberately garbled OCR-style text in the test set
100%
tamper attempts caught
we corrupted our own ledger to check. It noticed immediately.
Neither extreme works

Manual AP is slow. A chatbot with a bank login is worse.

Manual AP

  • Invoices sit in an inbox for days waiting on someone to notice them
  • PO matching is a person cross-referencing three systems by hand
  • Approval hierarchies live in someone’s memory, not in any system
  • By the time fraud is noticed, the money is already gone

A model with a bank login

  • The same reasoning that reads the invoice also decides whether to pay it
  • A cleverly worded PDF is one prompt injection away from an approval
  • “Trust the agent’s judgment” is not an audit trail a controller can sign off on
  • When something goes wrong, the only record is a conversation transcript

AP Autopilot separates reasoning from authority: no process that reads an invoice can also pay one.

The path one invoice takes

Seven steps. One of them a language model never touches.

Every invoice becomes one durable Temporal workflow the moment it arrives. It survives a crash, a deploy, a three-day wait on an approver, and resumes exactly where it left off.

01

Ingest

A durable workflow starts. Nothing after this point can be lost to a restart.

02

Extract

Vendor, amount, PO number, bank details parsed out of the document.

03

Validate

Checked against the accounting system’s PO / goods-receipt records, and against our own history for duplicates.

04

Score risk

Vendor history, bank-detail changes, round-number and split-invoice patterns, scored deterministically.

05

Gate

A Go rule engine decides: auto-approve, escalate, or reject. Same inputs, same answer, every time.

no LLM past this point
06

Pay / wait

Cleared invoices are paid immediately. Everything else waits, durably, for a named human.

07

Record

Every step is appended to a hash-chained ledger. Nothing here can be quietly edited later.

Every box below is real code, not a pitch diagram

The full decision flow: branches, waiting, and all.

Traced directly from the workflow’s own source. Rounded boxes are automated steps, the six-sided box is the one decision point, and filled pills are where an invoice’s story ends. The gold dot marks every step that also gets appended to the hash-chained audit ledger.

AUDIT LEDGERhash‑chainedInvoice received: email, upload, or forwarded PDFIngestdurable Temporal workflow startsMODELExtract fieldsvendor · amount · PO · bankMODELScore fraud riskheuristics + anomaly modelMCPValidatePO / receipt match · duplicatesPOLICY GATEdeterministic, no LLM past hereREJECTAUTO_APPROVEESCALATEAUTO-REJECTEDnotified · stoppedMCPNotify approverSlack / emailAwaiting decisionwaits durably, even daysno answer → escalates a tierApproved?yesnoREJECTED BY APPROVERnotified · stoppedExecute paymentthe only door to moneyfailedPAYMENT FAILEDno silent retrysettledReconcilevendor stats & bank historyPAID & RECONCILEDsettled · ledger closed

Run a real invoice through this exact path on /demo.

Shapes
automated step
decision point
end state
Path colors
auto-approve / success
escalated to a human
rejected / failed
Badges
written to the audit ledger
MODELmay involve a model
MCPexternal tool call
The one gate

Everything above the gate can be probabilistic. The gate itself and everything below it (approve, escalate, pay) is deterministic Go code with no model in its call stack.

Speaks to what you already run

Built to plug into your stack, not replace it.

Accounting
QuickBooksXeroNetSuite
Payments
Stripe TreasuryACH / bank rails
Notifications
SlackEmail

Every one of these is reached through the Model Context Protocol behind one stable tool contract, a swappable pattern we’ve built and run against sandboxed equivalents, not a claim of official partnership. Change providers without touching the workflow logic that calls them.

What your controller sees

The same dashboard that runs this pitch runs your invoice mix.

These four numbers come from actually running a 26-invoice adversarial corpus through the live system, not a hand-picked demo run.

0%
False-approve rate
Nothing that should have escalated or been rejected slipped through as auto-approved.
21.4%
False-escalate rate
When OCR-style noise got too garbled to trust, it asked a human instead of guessing.
94.2%
Field extraction accuracy
Vendor, amount, PO number, invoice number: checked against ground truth.
0.5s
Avg. time to resolution
From submission to either a payment or a named approver’s queue.

Typical time to a decision

Manual AP
3–5 days
AP Autopilot
0.5 sec

“Manual AP” reflects a typical email-and-spreadsheet approval cycle, not a measured benchmark. AP Autopilot’s figure is measured, for the subset of invoices that clear autonomously. Everything else still moves to a human in seconds, not days.

How the leash actually works

Bounded autonomy isn’t a prompt. It’s an architecture.

“No process that can reason can also pay.”

Exactly one component in the entire system holds credentials to the payment rail, and it has no language model anywhere in its call stack.

“The gate is boring on purpose.”

Policy decisions run through a small, deterministic, unit-tested Go service, auditable without reading a single token of model output.

“Nothing gets edited quietly.”

Every event is append-only and hash-chained to the one before it. We tested this by corrupting our own database. It caught it instantly.

“Swap the rails, not the workflow.”

Every external system is reached over MCP behind a stable tool contract. Change providers without touching the workflow that calls them.

“Every vendor has a memory, not a blank slate.”

Average invoice amount, prior bank details, submission cadence: it all persists per vendor and feeds every future risk score. A first invoice from a vendor is scored differently from the fortieth, and a bank-detail change against that memory is exactly what trips the gate.

Built on, not around

The infrastructure choices, and why each one is there.

Temporal

Durable execution: a three-day approval wait survives a worker restart with zero custom recovery code.

Go

The policy gate. Deterministic, fast, and easy to unit-test in complete isolation.

MCP

Every external tool call (accounting, payments, Slack) behind one uniform, swappable contract.

PostgreSQL

The append-only ledger, tenant isolation via row-level security, and every read model the dashboard shows.

Next.js

The live dashboard your team actually watches: approval queue, audit explorer, trust metrics.

This is a real, running system

Built end to end. Tested end to end.

Every number on this page came from actually running the system, including a bug we found and fixed by watching it hang, not from a slide deck. If you’re evaluating AP automation and want to see how the pieces actually fit together, get in touch.

Thanks, there. That’s saved on this page for this visit. Reach out any time to talk through the architecture.

This form runs entirely in your browser and doesn’t send data anywhere. It’s a portfolio piece. The product it describes is real and fully running.