# Three-Way Match Exceptions: Why Invoices Fail the PO and Receipt Check, and How to Clear Them Faster

> Invoices that fail three-way match pile up and stall payment. See why PO, receipt and invoice disagree, how to set tolerances, and how to clear exceptions.

- Source: https://parserai.co/blog/three-way-match-exceptions-po-receipt-invoice-accounts-payable
- Published: 2026-10-04

---
Three-way match is the control every accounts payable team says it has: pay an invoice only when it agrees with the purchase order and with what was actually received. The control is sound. The trouble is the exception queue it produces, a growing list of invoices that failed the match for reasons nobody has had time to read, holding up suppliers who were mostly right. This post looks at why invoices fail three-way match, how to set tolerances that mean something, and how to clear most exceptions without a person opening three PDFs.

Key takeaways

- A three-way match compares the purchase order, the goods receipt and the supplier invoice, and approves the invoice only when quantity and price agree within tolerance.
- Most match exceptions are not overbilling: they come from partial deliveries, unit-of-measure differences, receipts not yet posted and invoice lines that do not map to PO lines.
- Tolerances should be set per line and per variance type, with both a percentage and an absolute cap, so small rounding clears and large errors never do.
- Extracting every invoice line with its PO reference, quantity, unit and unit price turns most exceptions into rules that resolve themselves before a person looks.

## What three-way match checks, line by line

The three documents each own one fact. The **purchase order** owns the agreed price and the ordered quantity. The **goods receipt**, posted by the warehouse or the requester, owns the quantity that actually arrived. The **supplier invoice** is the claim. A match is approved when, for every invoice line, the quantity billed does not exceed the quantity received, and the unit price billed agrees with the purchase order within an allowed tolerance.

The words "for every invoice line" carry most of the weight. A header-level match, where the invoice total is compared with the PO total, is quick and almost useless: it approves an invoice that bills too much of one item and too little of another, and it rejects a perfectly correct invoice for a partial delivery. Real three-way match works at line level, which means every invoice line has to be tied to a specific PO line and to the receipts posted against it.

3

records per line: PO line, receipt, invoice line

2

tests per line: quantity against receipt, price against PO

1

reason to stop payment: a variance you cannot explain

## Why invoices fail the match

When teams finally sort their exception queue by cause, the result is usually humbling. Overbilling, the risk the control was built for, is a small slice. Most exceptions are timing and translation problems: the same purchase described three different ways, at three different moments.

### The receipt has not been posted yet

The goods arrived on Tuesday, the invoice arrived on Wednesday, and the receipt will be posted when someone at the dock catches up. Until then the match fails on quantity, the invoice waits, and on Friday a person in AP emails the warehouse to ask whether the delivery happened. This single cause can account for a large share of exceptions, and it resolves itself if the match is simply retried after the receipt lands.

### Partial deliveries and split invoices

The supplier shipped 150 of 200 units and invoiced 200, or shipped everything but invoiced in two parts. The first is a real quantity exception that should hold the unreceived part only. The second fails a naive match because the invoice line quantity does not equal the PO line quantity, even though cumulative invoiced quantity is still within what was received.

### Invoice lines that do not map to PO lines

The PO lists a part number, the invoice lists the supplier's own SKU and a description. The PO has one line for an assembly, the invoice breaks it into components. Or the invoice has no PO reference at all, or a PO number in the body text instead of the field where the AP system expects it. Without a line mapping there is nothing to compare, and the invoice falls straight to a person.

### Units of measure

The PO orders 600 each at 0.368, the invoice bills 12 boxes of 50 at 18.40. Both are correct, and a match that compares raw numbers flags a 2,000 percent price variance. Unit-of-measure conversion is dull, deterministic, and one of the most common sources of false exceptions.

### Price changes and real errors

A supplier raised the price after the PO was cut, or applied last year's price list, or the buyer agreed a new price by email and never updated the PO. Some of these are legitimate and need a PO change; some are errors that should be short-paid. Together with duplicates and genuine overbilling, this is the part of the queue that deserves a person's judgment.

_Illustrative share of three-way match exceptions by root cause. Numbers are examples, not measured results._

## Setting tolerances that mean something

A tolerance is a statement about which differences are not worth a person's time. Set too tight, every rounding difference becomes an exception and the queue trains people to approve without reading. Set too loose, the control quietly stops controlling. A few principles keep tolerances honest.

- **Separate price from quantity.** A small price variance is often acceptable; billing for more units than were received is almost never acceptable, whatever the amount. Quantity tolerance on received goods is usually zero or close to it.
- **Use a percentage and an absolute cap together.** Two percent of a ten-dollar line is noise. Two percent of a two-hundred-thousand-dollar line is four thousand dollars. Approve within tolerance only when both the percentage and the dollar amount are under their limits.
- **Apply it per line, not per invoice.** Header tolerances let line errors cancel each other out.
- **Vary it by category.** Commodity materials with index-linked pricing need different limits from fixed-price services or capital equipment.
- **Treat freight, tax and surcharges as their own lines.** They follow the terms on the PO, such as prepaid or prepay-and-add freight, not the unit price of the goods.

Tolerance is not a write-off budget

If the same supplier lands just under the price tolerance on every invoice, the tolerance is being used, not respected. Track approved variances per supplier over time, not only rejected ones.

## A workflow that clears most exceptions on its own

The pattern is the same one that works for any document-heavy reconciliation: get the invoice into structured lines first, apply deterministic rules for the causes you can explain, and route only what is left to a person, with the evidence attached.

### 1. Extract every invoice line, not just the total

Supplier number, invoice number and date, every PO number on the page, and for each line: supplier SKU, description, quantity, unit of measure, unit price and amount, plus freight, tax and other charges as separate lines. Defining these fields once, with types and required flags, is what makes the rules dependable. The post on [designing extraction schemas](https://parserai.co/blog/extraction-schema-design-field-types-versioning) covers how to model line items so new supplier layouts do not break them.

### 2. Map invoice lines to PO lines

Match on PO line reference when the invoice prints one, then on SKU through a supplier part cross-reference, then on description plus quantity and price as a fallback that a person confirms once and the system remembers. Convert units of measure before comparing anything.

### 3. Run the rules and explain each result

Cumulative invoiced quantity is no more than cumulative received quantity. Unit price is within the line's tolerance. Charges are allowed by the PO terms. The invoice number has not been paid before for this supplier. Each rule returns pass or fail with the expected and billed values, so the result explains itself.

### 4. Hold what is unreceived, pay what is matched, retry automatically

An invoice does not have to be all or nothing. Lines that match can be released while unreceived quantity is held, and held lines are retried automatically when new receipts post, before anyone emails the warehouse.

three-way-match.json — example result for one invoice

```
{
  "invoice": {
    "supplier": "Example Industrial Supply",
    "invoice_number": "SI-220481",
    "po_reference": "PO-77310",
    "currency": "USD",
    "lines": [
      { "line": 1, "sku": "BRG-6204", "description": "Ball bearing 6204-2RS",
        "qty": 200, "uom": "EA", "unit_price": 3.15, "amount": 630.00 },
      { "line": 2, "sku": "BLT-M10", "description": "Hex bolt M10x40, box of 50",
        "qty": 12, "uom": "BOX", "unit_price": 18.40, "amount": 220.80 }
    ],
    "freight": 45.00,
    "total": 895.80
  },
  "purchase_order": {
    "po_number": "PO-77310",
    "lines": [
      { "line": 10, "sku": "BRG-6204", "qty": 200, "uom": "EA", "unit_price": 3.10 },
      { "line": 20, "sku": "BLT-M10", "qty": 600, "uom": "EA", "unit_price": 0.368 }
    ],
    "freight_terms": "prepaid_and_add"
  },
  "goods_receipts": [
    { "receipt": "GR-5521", "po_line": 10, "qty": 150, "uom": "EA" },
    { "receipt": "GR-5521", "po_line": 20, "qty": 600, "uom": "EA" }
  ],
  "checks": [
    { "invoice_line": 1, "po_line": 10, "rule": "qty_le_received",
      "invoiced": 200, "received": 150, "status": "fail" },
    { "invoice_line": 1, "po_line": 10, "rule": "price_within_tolerance",
      "variance_pct": 1.61, "tolerance_pct": 2.0, "status": "pass" },
    { "invoice_line": 2, "po_line": 20, "rule": "uom_converted",
      "invoiced": "12 BOX", "converted": "600 EA", "status": "pass" },
    { "invoice_line": 2, "po_line": 20, "rule": "price_within_tolerance",
      "invoiced_unit": 0.368, "po_unit": 0.368, "status": "pass" },
    { "rule": "freight_allowed_by_terms", "status": "pass" }
  ],
  "decision": "hold_line_1_pending_receipt",
  "payable_now": 265.80,
  "on_hold": 630.00
}
```

In this example the bolts are billed in boxes and ordered in units, and after conversion the line matches exactly. The bearings are within the two percent price tolerance, but 200 were invoiced and only 150 have been received. Instead of the whole invoice sitting in a queue, the matched line and the freight are payable now, and the bearing line waits for the next receipt to post.

_Illustrative days from invoice receipt to approval, manual exception handling versus structured extraction with rule-based matching. Numbers are examples, not measured results._

## Measure the queue, not just the throughput

The useful numbers are the share of invoices that match on first pass, the share of exceptions that clear without a person, the age of the oldest open exception and the root cause of each one a person resolves. Root causes tell you where to fix upstream: a warehouse that posts receipts late, a buyer who changes prices by email, a supplier whose invoices never carry a PO number. Fixing the process removes exceptions; tuning tolerances only hides them.

Trust the extraction numbers before trusting the automation. Build a small labeled set of real invoices, with difficult layouts and multi-page line tables, and [measure field-level accuracy](https://parserai.co/blog/document-extraction-accuracy-field-level-eval-set) on quantity, unit and unit price in particular. A misread quantity becomes a false exception or, worse, a false match. When invoices arrive bundled with packing slips and delivery notes in one PDF, [splitting and classifying](https://parserai.co/blog/document-splitting-classification-mixed-pdf-batches) them first keeps a packing slip quantity from being read as a billed quantity. And at month-end, the [vendor statement reconciliation](https://parserai.co/blog/vendor-statement-reconciliation-supplier-ledger-accounts-payable) catches the invoices that never reached the match at all.

## Before you automate: a short checklist

- Match at line level, never only on invoice totals.
- Keep quantity tolerance on received goods at or near zero.
- Combine a percentage price tolerance with an absolute cap per line.
- Convert units of measure before comparing quantity or price.
- Keep a supplier part cross-reference so invoice SKUs map to PO lines.
- Release matched lines and hold only what is unreceived.
- Retry held lines automatically when new receipts post.
- Record a root cause for every exception a person resolves, and review it monthly.

## Where extraction fits

The matching rules in three-way match are not complicated, and most ERPs already run them. What breaks them is the input: supplier invoices in hundreds of layouts, with line tables that span pages, PO numbers in the wrong place and units nobody standardized. Parser extracts each invoice into structured JSON against the schema you define, line by line, so the match starts from fields it can compare and the exception queue holds only the invoices that really need a person.

Accounts Payable

## Bring a real invoice.

An invoice parser for accounts payable: invoices and bills arrive by upload, e-mail or API, and the fields you define are extracted and checked against your validation rules before they reach your system.

[Book a demo](https://parserai.co/demo?icp=ap)
## FAQ

### What is a three-way match in accounts payable?

It is a control that approves a supplier invoice for payment only when it agrees with two other records: the purchase order that set the quantity and price, and the goods receipt that confirms what was actually delivered. Quantity is checked against the receipt and price against the purchase order.

### What is the difference between two-way and three-way matching?

Two-way matching compares the invoice with the purchase order only, so it checks price and ordered quantity but not delivery. Three-way matching adds the goods receipt, so you pay only for what was received. Four-way matching adds an inspection or quality acceptance record.

### What is a reasonable price variance tolerance for three-way match?

Many teams start with a small percentage, such as one or two percent, combined with an absolute cap per line, so that rounding and minor freight or currency differences clear while a large dollar error is always reviewed. The right numbers depend on spend category and should be tuned from exception data.

### Why do so many invoices fail three-way match?

Usually because the documents describe the same purchase differently, not because the supplier overbilled. Partial shipments, receipts posted late, different units of measure, bundled or split invoice lines and missing PO references are the most common causes.

