Call overdue Xero customers with an AI collections agent
Every weekday at 10am, an AI voice agent phones your most overdue Xero accounts, logs what each customer promised, and reports back to finance in Slack.
Every weekday at 10am, sweep Xero for overdue sales invoices and have my LiveKit collections voice agent phone the worst offenders, then log and report every attempt. This is the phone call escalation tier that sits after email reminders, so treat it as a real collections process with real compliance rules, not a blast dialler.
Build the call list with Xero List Invoices, filtered to accounts receivable invoices with status AUTHORISED and a due date in the past, and work from the amount still outstanding on each one rather than the invoice total. Keep only invoices that are more than 14 days past due and where the outstanding balance is at least $500. Both numbers should be easy to change at the top of the workflow.
Before dialling anything, read the existing rows of the Google Sheets collections call log with Get Values and drop any invoice that has already been called in the last seven days. Also drop anything flagged as disputed or on a payment plan, whether that flag lives in the Xero invoice reference, the contact notes, or a status column in the sheet. Any invoice with an outstanding balance above $25,000 never gets an automated call: set it aside for a person and surface it in the Slack summary instead. Cap the run at 25 calls, worked oldest and largest first, and if one customer has several qualifying invoices, call them once about the oldest one while mentioning the total they owe.
For every invoice that survives the filters, call Xero Get Contact with the invoice's contact ID to pull the customer's phone number and email address. If there is no usable phone number on the contact, skip the call, send a copy of the invoice with Xero Email Invoice, and log the attempt as no phone on file.
To place a call, open a LiveKit room with Create Room with recording enabled and a room name that ties back to the invoice number. Then use Create Agent Dispatch to send my collections voice agent into that room, and put the invoice number, customer name, amount outstanding, currency, due date, and days overdue into the dispatch metadata so the agent already knows the account before the customer says hello instead of looking anything up mid call. Finally use Create SIP Participant to dial the customer's number into that same room.
After dialling, check List Participants on the room to confirm the customer actually joined. If no SIP participant connects within about 45 seconds, treat the attempt as no answer, tidy up with Delete Agent Dispatch, and move on to the next account.
The agent's opening line is not optional. It must state that it is an automated assistant calling on behalf of my company about an unpaid invoice, and that the call is being recorded, before it asks for anything. During the call it may confirm the invoice details, ask for a specific payment date, take a dispute reason, and offer to email a copy of the invoice. It must never agree to a discount, a write off, a new payment plan, or any other change of terms. A request like that ends the call politely with a promise that someone from finance will follow up.
When the call ends, find the recording with LiveKit List Egress for that room, wait for the egress to reach a completed state, and send the resulting audio file to Deepgram Transcribe Pre-recorded Audio with smart formatting and speaker labels turned on.
Read the transcript and classify the call as exactly one of: promise to pay, with the specific date the customer gave; dispute, with the reason in their own words; wrong number; or no answer. Quote the key line from the transcript verbatim so a human can sanity check the classification without listening to the recording. If the customer asked for a copy of the invoice, or if nobody picked up, send one with Xero Email Invoice.
Log every attempt, connected or not, as one row in the Google Sheets collections call log with Append Values: date and time, invoice number, customer name, amount outstanding, days overdue, number dialled, whether the call connected, outcome, promised payment date, the quoted line from the transcript, a link to the recording, and the next action.
Finish with a Slack Send a Message to the finance channel. Lead with who promised what and by when, then the total dollars covered by promises made this morning, then the accounts that need a human to step in: disputes, wrong numbers, repeat no answers, and the large balances that were deliberately held back from the voice agent. Keep it scannable, with the dollar amount and invoice number on every line.
Only place calls inside local business hours for the customer, defaulting to 9am to 5pm in their time zone based on the address on the Xero contact. If an account falls outside that window when its turn comes, leave it for the next run rather than calling late. If Xero, LiveKit, Deepgram, or the sheet fails partway through, still post the Slack summary with what did happen and a note about what broke.
What does this prompt do?
- Checks Xero every weekday morning for approved invoices that are past due, then builds a call list from the accounts that are more than two weeks late and over your dollar threshold.
- Places a real phone call to each one with your AI voice agent, which opens by saying it is an automated assistant and that the call is recorded, and already knows the invoice number, amount and due date before the customer picks up.
- Transcribes every call and sorts the result into promise to pay with a date, dispute, wrong number, or no answer, quoting the line the customer actually said.
- Writes every attempt to a Google Sheets call log, re-sends the invoice by email when it is asked for or nobody picks up, and posts a Slack wrap-up of who promised what and which accounts need a person.
What do I need to use this?
- A Xero account with access to your sales invoices and customer contact records
- A LiveKit project with outbound calling set up and your collections voice agent running
- A Deepgram account for turning call recordings into text
- A Google Sheet to hold the call log, and a Slack channel for the finance summary
- Phone numbers saved on your Xero customer records, since that is where the agent gets the number to dial
How can I customize it?
- The thresholds that decide who gets a call: how many days overdue (14 by default) and the smallest balance worth phoning about.
- The calling window and time zone, so calls only land inside your customers' normal business hours.
- The balance above which a person calls instead of the voice agent, plus how many calls to place in a single morning.
FAQs
Will the customer know they are talking to a machine?
What happens when nobody answers?
Can the agent agree to a discount or a new payment plan?
How does it avoid calling the same customer over and over?
Do the biggest accounts get called by the voice agent too?
Does this work if my customers are in different time zones?
Related templates
See every Google Maps listing you manage on one screen, ranked worst first, with an audit button that writes the fix list for you.
Every couple of hours we find the chats your team never answered, email those visitors a real reply, and hand the sensitive ones to a support lead.
Your team picks a template, finds the customer, checks they are safe to email, then sends it, with every send logged where the whole team can see it.
Every night at 2am, pull the contacts on your open and won deals and block them from your cold outreach before the next send goes out.
Watch every live room on one screen, remove disruptive guests, start recordings and end stuck sessions without anyone opening a terminal.
Build every text campaign in one screen: check who is actually reachable, see a realistic send plan, then watch delivery land row by row.
Stop working your aged receivables one phone call at a time.
Set your thresholds once and let the voice agent call the overdue accounts every morning, with every promise logged and every exception routed to your team.