Airtable + Vapi: outbound calls with notes logged
Manual outbound follow-up falls apart fast. One lead gets called, the next gets skipped, and the notes end up in five different places (or nowhere at all).
This is the kind of mess that hits sales ops first, but founders and agency owners feel it too. With Airtable Vapi automation, your “to be called” list turns into real call attempts, and every transcript and summary lands back on the right lead record.
Below, you’ll see how the workflow runs, what results to expect, and what you need to get it live without turning your CRM into a junk drawer.
How This Automation Works
The full n8n workflow, from trigger to final output:
n8n Workflow Template: Airtable + Vapi: outbound calls with notes logged
flowchart LR
subgraph sg0["Flow 1"]
direction LR
n5["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/webhook.dark.svg' width='40' height='40' /></div><br/>Vapi Callback Webhook"]
n6["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Log Raw Call Data"]
n7["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Update: Call Connected"]
n8["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Update: Call Failed"]
n9["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Update: Lead Unreachable"]
n10["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Log: Voicemail Attempt 3"]
n11["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Log: Voicemail Attempt 2"]
n12@{ icon: "mdi:swap-horizontal", form: "rounded", label: "Filter: Was Answered?", pos: "b", h: 48 }
n13@{ icon: "mdi:swap-horizontal", form: "rounded", label: "Check: Is Voicemail?", pos: "b", h: 48 }
n14@{ icon: "mdi:swap-horizontal", form: "rounded", label: "If First Call", pos: "b", h: 48 }
n15@{ icon: "mdi:swap-horizontal", form: "rounded", label: "If Second Call", pos: "b", h: 48 }
n16@{ icon: "mdi:swap-horizontal", form: "rounded", label: "If Third Call", pos: "b", h: 48 }
n17["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/httprequest.dark.svg' width='40' height='40' /></div><br/>Retry: Call #2"]
n18["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/httprequest.dark.svg' width='40' height='40' /></div><br/>Retry: Call #3"]
n19["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Get Lead ID #1"]
n20["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Get Lead ID #2"]
n21["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Get Lead ID #3"]
n22@{ icon: "mdi:swap-horizontal", form: "rounded", label: "Is End Report?", pos: "b", h: 48 }
n23["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Log: Voicemail Attempt 1"]
n24@{ icon: "mdi:cog", form: "rounded", label: "Wait: 1 Minute", pos: "b", h: 48 }
n25@{ icon: "mdi:cog", form: "rounded", label: "Wait: Next Day 4pm", pos: "b", h: 48 }
n14 --> n23
n14 --> n15
n16 --> n25
n16 --> n9
n19 --> n7
n20 --> n14
n21 --> n8
n15 --> n23
n15 --> n16
n22 --> n6
n17 --> n11
n18 --> n10
n24 --> n17
n6 --> n12
n25 --> n18
n13 --> n20
n13 --> n21
n12 --> n19
n12 --> n13
n5 --> n22
n23 --> n24
end
subgraph sg1["Schedule Every Minute Flow"]
direction LR
n0@{ icon: "mdi:play-circle", form: "rounded", label: "Schedule Every Minute", pos: "b", h: 48 }
n1["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Fetch TBC Leads"]
n2@{ icon: "mdi:swap-vertical", form: "rounded", label: "Prepare Call Metadata", pos: "b", h: 48 }
n3["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/httprequest.dark.svg' width='40' height='40' /></div><br/>POST: Trigger Vapi Call"]
n4["<div style='background:#f5f5f5;padding:10px;border-radius:8px;display:inline-block;border:1px solid #e0e0e0'><img src='https://flowpast.com/wp-content/uploads/n8n-workflow-icons/airtable.svg' width='40' height='40' /></div><br/>Update Lead: In Progress"]
n1 --> n2
n2 --> n3
n0 --> n1
n3 --> n4
end
%% Styling
classDef trigger fill:#e8f5e9,stroke:#388e3c,stroke-width:2px
classDef ai fill:#e3f2fd,stroke:#1976d2,stroke-width:2px
classDef aiModel fill:#e8eaf6,stroke:#3f51b5,stroke-width:2px
classDef decision fill:#fff8e1,stroke:#f9a825,stroke-width:2px
classDef database fill:#fce4ec,stroke:#c2185b,stroke-width:2px
classDef api fill:#fff3e0,stroke:#e65100,stroke-width:2px
classDef code fill:#f3e5f5,stroke:#7b1fa2,stroke-width:2px
classDef disabled stroke-dasharray: 5 5,opacity: 0.5
class n0 trigger
class n12,n13,n14,n15,n16,n22 decision
class n6,n7,n8,n9,n10,n11,n19,n20,n21,n23,n1,n4 database
class n5,n17,n18,n3 api
classDef customIcon fill:none,stroke:none
class n5,n6,n7,n8,n9,n10,n11,n17,n18,n19,n20,n21,n23,n1,n3,n4 customIcon
The Problem: Outbound Follow-Ups Don’t Scale (And Notes Get Messy)
Outbound calling sounds simple until you try to do it consistently. Someone exports a list, someone else dials, and then the “notes” live in a call tool, a Slack message, a spreadsheet, and somebody’s memory. Meanwhile, leads marked “call later” sit for days because nobody owns the next attempt. Even when calls happen, you still have to listen back for key details, write a summary, and paste it into Airtable. That’s a lot of small steps, and they steal time from actual selling.
It adds up fast. Here’s where it breaks down in real teams.
- You lose about 5–10 minutes per lead just switching between dialer, notes, and Airtable.
- Voicemails don’t get retried consistently, so your best leads quietly expire.
- Call notes are subjective and incomplete, which means follow-ups sound different depending on who called.
- Without transcripts and recordings attached to the record, coaching and QA become guesswork.
The Solution: Airtable-Driven AI Calls With Automatic Call Logging
This workflow turns Airtable into a simple outbound engine. Every minute, n8n checks your Leads table for records marked “TBC” (to be called). When it finds one, it assembles the call details (name, phone number, context) and triggers a Vapi AI outbound call. After the call ends, Vapi posts back to a webhook in n8n with the full payload, including the recording, transcript, and an AI summary. n8n then updates the same Airtable record so your team can see what happened without hunting.
Calls that hit voicemail aren’t treated like failures. The workflow runs a built-in retry sequence: it re-dials after about a minute, then makes a final attempt the next day, and finally marks the lead unreachable if nobody ever answers.
What You Get: Automation vs. Results
| What This Workflow Automates | Results You’ll Get |
|---|---|
|
|
Example: What This Looks Like
Say you have 25 new leads to qualify in Airtable each day. Manually, a rep might spend about 3 minutes per lead just dialing, waiting, and logging notes, which is roughly 75 minutes before you count any actual conversation time. With this workflow, the “admin” part shrinks to almost nothing: mark leads as TBC, let Vapi call, and review the summary when it’s done. Even if you spend 30 seconds skimming each summary, that’s around 10–15 minutes of review instead of an hour-plus of busywork.
What You’ll Need
- n8n instance (try n8n Cloud free)
- Self-hosting option if you prefer (Hostinger works well)
- Airtable to store leads and call outcomes.
- Vapi to place AI outbound calls.
- Vapi API key (get it from your Vapi dashboard settings).
Skill level: Intermediate. You’ll connect accounts, map a few Airtable fields, and paste in a webhook URL.
Don’t want to set this up yourself? Talk to an automation expert (free 15-minute consultation).
How It Works
Airtable status triggers the work. Every minute, n8n scans your Leads table for records marked “TBC”, so your team has a single, obvious “call queue” field.
Lead context gets packaged for the call. n8n pulls the lead’s mobile number and any extra context you store (source, notes, segment), then passes it into the Vapi call request using an HTTP step.
Vapi calls, then reports back. After the call finishes, Vapi hits your n8n webhook with the transcript, recording link, and an AI-generated summary. The workflow verifies the report, then stores the payload on the correct Airtable record.
Retries happen automatically when it’s voicemail. If the workflow detects voicemail, it delays about a minute and re-dials, then schedules a final attempt the next day. After that, it updates the record so your team sees “unreachable” instead of endlessly retrying the same lead.
You can easily modify the Airtable status names and retry timing to match your process. See the full implementation guide below for customization options.
Step-by-Step Implementation Guide
Step 1: Configure the Schedule Trigger
Set the workflow to check for pending leads every minute.
- Add the Minute Interval Trigger node and set the interval rule to
minuteswithminutesInterval: 1. - Confirm the connection flow goes from Minute Interval Trigger to Retrieve Pending Leads.
Step 2: Connect Airtable and Fetch Pending Leads
Pull leads marked as “TBC” from Airtable and prepare the base record data.
- Open Retrieve Pending Leads and set Operation to
search. - Set Filter By Formula to
({Status} ='TBC')and Limit to10. - Credential Required: Connect your Airtable credentials for Retrieve Pending Leads and all other Airtable nodes (12 total handling lead lookup and status updates).
Step 3: Set Up Call Payload Assembly and Initial Call
Build the call payload and initiate the first Vapi call, then mark the lead as in progress.
- In Assemble Call Details, add assignments for ID =
{{ $json.id }}, First Name ={{ $json["First Name"] }}, and Mobile ={{ $json.Mobile }}. - Configure Initiate Vapi Call with URL
https://api.vapi.ai/call, MethodPOST, and JSON Body set to{ "assistantId": "[YOUR_ID]", "customer": { "name": "{{ $json['First Name'] }}", "number": "{{ $json.Mobile }}" }, "phoneNumberId": "[YOUR_ID]" }. - In Initiate Vapi Call header parameters, set Authorization to
Bearer [CONFIGURE_YOUR_TOKEN]. - In Mark Lead In Progress, set Operation to
updateand map id to{{ $('Assemble Call Details').item.json.ID }}with Status =In progress.
[CONFIGURE_YOUR_TOKEN] with your real API token.Step 4: Configure the Vapi Callback and Store Results
Handle Vapi’s callback payload, verify the end-of-call report, and store call details in Airtable.
- Configure Vapi Callback Endpoint with HTTP Method
POSTand Pathvapi-callback. - In Verify End Report, set the condition to Left Value
{{ $json.body.message.type }}equals Right Valueend-of-call-report. - In Store Call Payload, set Operation to
createand map fields: id ={{ $json.body.message.call.id }}, recording ={{ $json.body.message.recordingUrl }}, transcript ={{ $json.body.message.transcript }}. - Ensure the flow continues from Store Call Payload to Check Answer Status.
Step 5: Configure Answer Logic, Voicemail Handling, and Retries
Route answered calls to success, and voicemail calls through retry logic with wait timers and attempt counters.
- In Check Answer Status, set the condition to Left Value
{{ $json.fields['ended reason'] }}notEqualscustomer-did-not-answer. - For answered calls, use Lookup Lead Record 1 with Filter By Formula
=({Mobile} = '{{ $("Verify End Report").item.json.body.message.call.customer.number }}'), then update status in Update Connected Status with Status =Called, Attempt =#Success, and Summary ={{ $('Verify End Report').item.json.body.message.analysis.summary }}. - For unanswered calls, set Detect Voicemail Result to check Left Value
{{ $('Verify End Report').item.json.body.message.endedReason }}equalsvoicemail. - Configure attempt routing: Lookup Lead Record 2 → Evaluate First Attempt (notExists) → Record Voicemail Attempt 1 (set Status
Voicemail, Attempt#1) → Delay One Minute (Amount1minutes) → Retry Call Attempt 2 (send customer name/number from{{ $json.fields['First Name'] }}and{{ $json.fields.Mobile }}). - Continue the retry chain: Retry Call Attempt 2 → Record Voicemail Attempt 2 (Attempt
#2) → Evaluate Second Attempt → Evaluate Third Attempt → Delay Until Next Day with Date Time{{ $now.plus(1, "day").setZone("Australia/Sydney").set({ hour: 16, minute: 0 }).toISO() }}→ Retry Call Attempt 3 → Record Voicemail Attempt 3 (Attempt#3). - If the third attempt fails, route via Lookup Lead Record 3 to Update Failed Status (Status
Failed, Summary from{{ $('Verify End Report').item.json.body.message.analysis.summary }}) or use Mark Lead Unreachable (AttemptUnreachable).
First Name, Mobile, Status, or Attempt, updates in Record Voicemail Attempt 1 and related nodes will silently fail.Step 6: Test and Activate Your Workflow
Verify the trigger, call flow, and Airtable updates before enabling production execution.
- Manually execute Minute Interval Trigger to confirm Retrieve Pending Leads returns records and Assemble Call Details formats the payload.
- Send a test call through Initiate Vapi Call and confirm the lead is updated by Mark Lead In Progress.
- Trigger the webhook using a sample Vapi payload to ensure Vapi Callback Endpoint → Verify End Report → Store Call Payload executes and Airtable records are created.
- Check that answered calls update via Update Connected Status and voicemail paths follow the retry chain.
- Activate the workflow by switching it to Active once tests complete successfully.
Common Gotchas
- Vapi credentials can expire or need specific permissions. If things break, check your Vapi API key and header auth in the n8n credential setup first.
- If you’re using Wait nodes or external call processing, timing varies. Bump up the wait duration if the webhook payload arrives late and downstream steps fail on empty data.
- Default prompts in AI nodes are generic. Add your qualification rules and brand voice early or you will be rewriting summaries and follow-ups forever.
Frequently Asked Questions
About 30–60 minutes if your Airtable base is ready.
No. You’ll mostly map Airtable fields and paste in your Vapi details. The HTTP and webhook parts are already handled in the workflow.
Yes. n8n has a free self-hosted option and a free trial on n8n Cloud. Cloud plans start at $20/month for higher volume. You’ll also need to factor in Vapi usage costs for calls and any OpenAI usage used for summaries.
Two options: n8n Cloud (managed, easiest setup) or self-hosting on a VPS. For self-hosting, Hostinger VPS is affordable and handles n8n well. Self-hosting gives you unlimited executions but requires basic server management.
Yes, and it’s honestly one of the best reasons to use n8n here. You can change the voicemail logic in the “Detect Voicemail Result” checks, adjust timing in the Wait steps (“Delay One Minute” and “Delay Until Next Day”), and update what gets written back in the Airtable “Update” nodes. Common tweaks include only retrying once, changing the “optimal time” window for next-day calls, and writing different statuses like “Needs human follow-up” for high-value accounts.
Usually it’s the Airtable token or base access. Confirm the credential in n8n still has permission to the right base, then double-check the table name and field names match exactly (Status, Mobile, Attempt, Summary). If records update but look wrong, it’s often a field type mismatch, like writing text into a single select.
A few hundred a day is realistic for most small teams, then your limiting factor becomes call capacity and API rate limits more than n8n.
Often, yes, because this flow has branching logic, retries, and webhook handling that gets awkward (and expensive) in simpler tools. n8n is happy doing “if voicemail, wait, retry, then schedule tomorrow,” and you don’t pay extra for every little path. Zapier or Make can still work if your needs are basic, like “call once, log summary,” and you value a simpler UI over control. The tradeoff is flexibility: when your sales process changes, you’ll want to edit logic, not rebuild it. Talk to an automation expert if you want help picking the right approach.
This workflow keeps outbound moving and Airtable clean, even when your day gets chaotic. Set it up once, then let the call attempts and call notes take care of themselves.
Need Help Setting This Up?
Our automation experts can build and customize this workflow for your specific needs. Free 15-minute consultation—no commitment required.