Invoices sit in approval for days: find the hop where it died
In short
Age each invoice at the hop it is sitting on rather than at the invoice, and the stall names itself: an approver who left, a delegation that expired, a threshold escalating to a role nobody holds, a cost-centre owner changed in the HR system but not in the routing matrix, or a notification filtered into a folder nobody opens.
Key takeaways
- Time-in-hop is the diagnostic field. Total invoice age mixes a wait for a receipt with a wait for a person.
- An invoice whose current hop has no resolvable principal is not late, it is lost, and no amount of chasing finds it.
- Resolve approvers against the live directory at routing time, never against a name copied into a rule months ago.
- Delegation has to be a dated record with a named backup, because a calendar out-of-office routes nothing anywhere.
- Every routing engine needs a dead-letter path: an explicit state, an owner and a clock, for invoices no rule can place.
An invoice does not stall. A hop stalls, and the invoice is simply the thing sitting at it. Once the workflow is instrumented per hop rather than per document, the population of stuck invoices separates within minutes into 5 causes, 4 of which are configuration faults nobody has looked at rather than approvers who are ignoring you.
The most important distinction the instrumentation gives you is between an invoice waiting on a person and an invoice waiting on nobody at all. The second kind never moves, no matter how many reminders are sent, because there is no recipient at the other end of the reminder.
Age the hop, not the invoice
The query below is the whole confirming check. It should be a standing view over the workflow tables, because a stall that has to be investigated by hand is a stall that gets investigated once.
- For every in-flight invoice, record the current hop: its index, its type (match, code, approve at level 1 upward, treasury release), the resolved principal as a directory identifier rather than a display name, the assignment timestamp, and the last notification attempt with its delivery result.
- Compute time-in-hop and sort on it. Total age is useless here: 6 days waiting on a goods receipt and 6 days waiting on a director are the same number and completely different problems.
- Group by resolved principal. One person holding 40 items is a workload; 40 people holding 1 item each is a cadence problem; a null principal on any of them is a routing failure.
- Cross-check each principal against the directory. Flag any that are disabled, marked as leavers, or have approved nothing in 30 days despite holding items.
- Group by the routing rule that produced the assignment, then by cost centre. A stall that follows a rule is a threshold or role fault; a stall that follows a cost centre is a master-data fault.
- Read the notification result on the stalled hop: sent, delivered, bounced, suppressed, opened. Delivered-and-never-opened is a different diagnosis from never-delivered, and both are different from never-sent.
Five ways an approval instruction dies in transit
| Cause | What the hop record shows | Structural fix | Owner |
|---|---|---|---|
| The approver has left | Principal resolves to a disabled directory account, assigned after their leaving date | Resolve approvers at routing time against the live directory, and revalidate on every retry rather than only at assignment | Identity and joiners-leavers process, with accounts payable systems |
| Delegation missing or expired | Principal is active but absent; no delegation record, or one whose end date has passed | Delegation as a dated record with a mandatory named backup per approver, enforced before leave is approved | Each approver's manager |
| Threshold escalates to a vacant role | The rule names a role; the role currently has no holder, so resolution returns nothing | Validate role-to-person resolution when the rule is saved, and define the level the rule falls through to | The approvals policy owner in finance |
| Cost-centre owner changed only in HR | Stalls follow one cost centre across suppliers and amounts, while every other cost centre flows | Derive owners from the system of record at routing time instead of a matrix copied into the workflow tool | Master data owner |
| Notification suppressed or unread | Delivered but never opened, or filtered; often an external-sender banner, a rule, or a digest that batches it away | Make the in-app queue the system of record and the email a pointer to it, then measure opens per approver | Accounts payable systems |
The approver who left in April and is still in the routing rule
This is the commonest cause and the least visible, because the rule looks perfectly valid: it names a person, that person once existed, and the workflow tool has no opinion about whether they still work here. The signature is a cluster of stalls that all began within 3 days of each other and share 1 principal, whose approval history stops abruptly.
The fix is not to update the rule; it is to stop storing people in rules. A rule should express a position — the owner of this cost centre, the manager of the requester, the finance lead for this entity — and resolve that position against the directory at the moment of routing. Where the requester was never captured at intake, there is nothing to resolve from in the first place, which makes this an ingestion defect wearing an approval costume; turning an invoice mailbox into a pipeline covers the fields intake has to carry forward.
A routing rule that names a person is a snapshot of an org chart taken on the day somebody wrote it. Everything after that day is drift.
Delegation that exists in the calendar and nowhere else
An out-of-office reply is not a delegation. The approver is active, reachable and technically able to act, so nothing in the workflow flags an anomaly — the item simply waits 2 weeks. Expiry is the sharper version of the same fault: a delegation that ended at midnight leaves items assigned to a person who is genuinely away, and the record that would have moved them is now inactive.
- Give delegation a start and an end. An open-ended delegation becomes a permanent transfer of authority nobody reviews, which is a controls problem rather than a convenience.
- Require a named backup on every approver record, so absence has a destination even when nobody set up a delegation.
- Re-resolve on retry. If an item was assigned before a delegation started, the retry should honour the delegation rather than the original assignment.
- Keep the original approver on the audit trail. Who was meant to approve, and who actually did, are 2 separate facts a controller will need later.
A threshold that escalates into an empty chair
Amount thresholds create hops that fire rarely. An invoice above the second threshold may route to a role held by one person, and if that role is vacant between hires, everything above the threshold stops while everything below it flows. It reads as a value-band problem, which is why it survives so long: the queue looks healthy on average and only the largest items are stuck.
Two changes remove it. Validate resolution when a routing rule is saved, so a rule pointing at an unfilled role cannot be activated. And define what a rule falls through to — the level above, an entity-level approver, or the dead-letter queue — rather than leaving the failure undefined. Getting the coding right upstream matters here too, because thresholds and owners are keyed to the cost centre the invoice was coded to, and a wrong code sends a correct rule to the wrong person; automatic coding to the general ledger covers what that step must and must not decide alone.
The notification that arrived and was never seen
This is the only cause of the five that is genuinely about people, and even then the fix is technical. Approval mail is high-volume, template-shaped and frequently sent from a system address, which is exactly the profile that collects mail rules, digest batching and external-sender warnings. Delivered-and-unopened across a whole approver population is not 40 individually careless managers; it is one filtering behaviour.
Treat email as a pointer and the in-app queue as the record. Measure per-approver open rates and treat a zero-open approver as a delivery defect rather than a compliance issue. And check what the message contains: a request missing the 3 facts an approver needs — purchase order reference, supplier, amount — forces them into a second system before they can act, which is a delay you built.
Resolve late, delegate by rule, and give lost invoices somewhere to go
- Resolve every approver at routing time and again at every retry, against the directory and the cost-centre owner in the system of record. Cache the resolution on the hop for audit, never for reuse.
- Make delegation and a named backup mandatory attributes of an approver record, with dates, and block leave workflows that would leave a position uncovered.
- Create a dead-letter state with an owner and a clock. Anything unroutable lands there within 24 hours, is worked by a named person, and exits with the rule that failed recorded against it.
- Alert on the rule, not on the invoice. If the same routing rule produces 3 unroutable items in a week, the rule is broken and the alert should go to whoever owns it.
An unroutable invoice is the accounts-payable version of a balance nobody owns: everyone can see it, no one is accountable for moving it, and it ages until someone is embarrassed by it. The same ownership discipline argued in who owns the balance when the processor disagrees applies here, and it is the reason the dead-letter path needs a person's name on it rather than a team's. Because resolution touches directory and HR records, some teams keep the routing layer entirely inside their own network, which is the deployment constraint weighed in private LLM deployment.
What a working router still cannot do
It will not decide your approval policy. Who must approve what, at which value, with what segregation of duties, is a controls decision that a routing engine executes rather than makes — and a badly designed policy routes flawlessly to too many people. Nor does it govern what happens after approval: releasing money is a separate control surface with its own checks, modelled end to end in a Thursday payment run.
It also does not tell you how the resulting queue should be staged and owned, which is the operating model in designing an exceptions-first approvals queue, and it will not stop the queue refilling if the upstream defects generating exceptions are still firing — the concentration analysis in the exception queue that grows faster than it clears. The whole flow sits inside invoice to pay: capture, matching and approvals; the routing and workflow systems we build for finance operations teams are scoped under AI agents and automation.
Frequently asked questions
Short answers to the follow-ups this page tends to raise.
Why do reminder emails not clear a stalled approval queue?
Because most stalls are not caused by an approver forgetting. If the hop resolves to a leaver, a vacant role or nobody at all, the reminder is addressed to someone who cannot act, and sending more of them changes nothing except the noise level. Reminders only work on the one cause they fit: an active, present approver who has seen the request and not acted.
How long should an invoice sit at one approval hop before it escalates?
Set the escalation clock from the payment terms rather than from a general service level, working backwards from the due date through the remaining hops and the payment run cadence. An invoice on 14-day terms with 3 hops left and a weekly run has very little slack; one on 60-day terms has plenty. A single fixed number across all invoices either escalates constantly or escalates too late.
Should approval authority be delegated automatically when someone is on leave?
Yes, provided the delegate is named in advance and the delegation is dated. Automatic delegation to whoever is available is a controls failure; a pre-agreed backup with a start and end date is simply the approval matrix expressed properly. Record both the intended approver and the actual one so the trail shows how authority moved.
What belongs in a dead-letter queue for invoices?
Anything the routing rules cannot place: no resolvable approver, no owner for the cost centre, a rule that errored, or an amount above every defined threshold. The queue needs a named owner, a maximum dwell time and an exit that records which rule failed, so the same configuration gap is fixed rather than manually worked around every month.
- approvals
- routing
- accounts payable
- diagnostics
The work behind this page
Builds from our portfolio that this page draws on.
Read next
- Your exception queue is growing: it is a defect list, not a headcount gapA queue that grows faster than it clears is almost never evenly spread. Pivot it by exception type against supplier and entity, and a handful of cells will be carrying most of the volume.diagnostic
- Matching fails because the goods receipt has not been posted yetAn exception that resolves itself if left alone for two days is not a receipting failure. Measure the site's receipting lag, then let the system wait instead of a person.diagnostic
- Non-PO invoices: what an automated flow can match them against insteadNo purchase order means no agreed quantity, price or delivery to join against. Four substitute commitments, in order of strength, and what each one lets a system clear.definition
- The invoice quantity is right and the match fails: unit-of-measure driftThe extraction is right, the totals reconcile, and the line still fails on quantity. When the ratio between the two quantities is a clean pack multiple, nobody is over-billing you.diagnostic
- The same invoice got paid twice: finding the near-duplicate your check missedThe exact-match check passed because the second document differed in one of the three fields it compares. Five ways one bill becomes two, the fuzzy key that catches each, and where the sweep belongs.diagnostic
- The vendor master record: the fields that decide whether an invoice can be automated at allSix field groups, four fields almost nobody has, and the reason one supplier ends up as five rows. Most AP automation failure is a vendor master problem wearing a matching costume.definition
Related across the site
Working on something in this space?
Tell us where you are in a sentence or two. We'll tell you honestly whether we're the right team, and what a sensible first slice of the work looks like.
Start the conversation