m4Mindset docs

Demos / Ops console · Brightline Supply

Invoice exceptions

Work through invoice exceptions with a scripted agent that compares invoice and PO and asks you to approve or query.

Brightline Supply is a made-up distributor, and this is its accounts-payable ops console. Six invoices stopped overnight: a price variance, a short shipment, a possible duplicate, one with no purchase order, and two small differences. The console on the left is ordinary React. The assistant on the right is a Mindset agent in the <mindset-agent> element. It is the same invoice exceptions agent the docs use as their running example.

The agent is configuration

The agent, invoice-exceptions, is five prompt fields, a model, a script and grants for five functions and one widget. There is no agent code. Its definition lives in the repo under demos/invoice-exceptions/ and is applied to the workspace through the admin MCP.

Five functions

Each function starts from literal sample data and runs pure steps after it, so it costs no model call and gives the same answer every time.

  • invoice-exceptions-list-exceptions returns today's queue.
  • invoice-exceptions-get-invoice and invoice-exceptions-get-po return one document.
  • invoice-exceptions-contract-terms returns a supplier's price tolerance and payment terms.
  • invoice-exceptions-compare pairs each invoice line with its purchase order line, works out what was billed against what was received at the agreed price, totals the variance, and checks it against the tolerance. It also flags a duplicate and a missing purchase order.

Comparing an invoice to a purchase order has one right answer, which is why it is a function. Whether to pay is a judgment, so it stays with the agent and the clerk. See Build a function.

One widget

invoice-exceptions-review is a widget: the invoice beside the purchase order, line by line, with the differing lines highlighted, the variance, the contract tolerance, an optional reason box and two buttons. Approve and Query supplier send a message back to the agent. The element draws the card natively, which is why this demo uses the element rather than the UI-less client.

The script

invoice-exceptions-flow has three phases. Fetch loads the queue on entry and offers three ways to start. Assess offers only the read functions and the card: the agent compares one invoice, shows it, and records invoiceId and its recommendation. Its gate is a check on those two values. Decide waits for the clerk. Only there is the page tool that records a decision offered, so the agent can't approve anything before the card is on screen. After Decide the script ends and the agent carries on with the rest of the queue. See Write a script.

Page tools and situational awareness

The page registers two page tools. resolve_exception takes an invoice, approve or query, and an optional reason, and changes the row's status chip. open_exception selects a row. Each one checks its arguments and returns an error string for an unknown invoice or decision.

Situational awareness sends the whole queue with each status, and the selected invoice, on every turn.

The console keeps to what the agent changes: the queue's status chips, the selected row, the open variance and a one-line Fetch, Assess, Decide indicator. The line-by-line comparison lives on the review card in the chat, not in a second pane on the page, and the three opening prompts are the script's own suggested replies, drawn by the element.

The progress indicator is not the script's own cursor, because the page receives no phase events. It is worked out from the run's tool calls for the selected invoice: Fetch once a document was read, Assess once the comparison ran and the card was shown, Decide once the status changed.

Under the hood

The pane below lists every function call with its arguments, the review card, and each page tool with the result the page returned.

Build the same thing

Start from Turn a skill or spec into an agent, then test the agent's behavior and put it on your page with the mindset-agent element.