Beginner~12 min setupProductivity & CRMVerified April 2026
Google Sheets logo
HubSpot logo

How to Reconcile Google Sheets Contacts Against HubSpot with Make

Compare contact lists between Google Sheets and HubSpot to identify missing records in either system and sync discrepancies.

Steps and UI details are based on platform versions at time of writing β€” check each platform for the latest interface.

Best for

Teams with 200+ contacts who need bidirectional comparison between Google Sheets and HubSpot with custom matching logic

Not ideal for

Simple one-way imports or teams with under 50 contacts where manual comparison is faster

Sync type

scheduled

Use case type

sync

Real-World Example

πŸ’‘

A 25-person marketing agency uses this to reconcile their prospect spreadsheet against HubSpot weekly. They import leads from events into Google Sheets but sales reps add contacts directly to HubSpot. Before automation, they spent 3 hours monthly comparing systems and missed 15-20 duplicate prospects. Now the scenario runs every Monday morning and flags discrepancies in a separate sheet for review.

What Will This Cost?

Drag the slider to your expected monthly volume.

/mo
505005K50K

Each platform counts differently β€” Zapier: 1 task per trigger. Make: 1 operation per module per record. n8n: 1 execution per run.

Prices shown for annual billing. Based on published pricing as of April 2026.

Estimated ROI

1000

min saved/mo

$583

labor value/mo

Free

no platform cost

Based on ~2 min manual effort per operation at $35/hr fully loaded labor cost.

Implementation

Skip the setup

Import this workflow directly into Make

Copy the pre-built Make blueprint and paste it straight into Make. All modules, filters, and field mappings are already configured β€” you just need to connect your accounts.

Before You Start

Make sure you have everything ready.

Google Sheets spreadsheet with contact data including email addresses
HubSpot account with contacts and API access enabled
HubSpot private app or API key with contacts read/write permissions
Make account with sufficient operations for your contact volume
Clean, consistent email formatting in both systems for accurate matching

Field Mapping

Map these fields between your apps.

FieldAPI Name
Required
Email Addressemail
5 optional fieldsβ–Έ show
First Namefirstname
Last Namelastname
Company Namecompany
Phone Numberphone
Lead Sourcehs_lead_source

Step-by-Step Setup

1

Dashboard > Create Scenario > Google Sheets

Create New Make Scenario

Start a new scenario in Make to build your contact reconciliation workflow. This will house all the modules needed to compare both systems.

  1. 1Click 'Create a new scenario' from your Make dashboard
  2. 2Click the large + button in the center
  3. 3Search for 'Google Sheets' and select it
  4. 4Choose 'Watch Rows' as your trigger
βœ“ What you should see: You should see a Google Sheets module with 'Watch Rows' selected as the trigger type.
2

Google Sheets Module > Connection

Connect Google Sheets Account

Authenticate your Google account so Make can access your contact spreadsheet. You'll need edit permissions on the sheet containing your contact list.

  1. 1Click 'Create a connection' in the Google Sheets module
  2. 2Sign in to your Google account when prompted
  3. 3Grant Make permission to access your Google Sheets
  4. 4Select 'Allow' for all requested permissions
βœ“ What you should see: The connection field should show 'My Google Sheets connection' with a green checkmark.
⚠
Common mistake β€” Don't use a shared service account here - personal auth works better for sheet access
Make settings
Connection
Choose a connection…Add
click Add
Google Sheets
Log in to authorize
Authorize Make
popup window
βœ“
Connected
green checkmark
3

Google Sheets Module > Configuration

Configure Google Sheets Trigger

Point Make to your specific contact spreadsheet and configure which changes should trigger the reconciliation process.

  1. 1Select your contact spreadsheet from the 'Spreadsheet' dropdown
  2. 2Choose the worksheet containing contacts (usually 'Sheet1')
  3. 3Set 'Table contains headers' to Yes
  4. 4Leave 'Row processing option' as 'Process all rows'
βœ“ What you should see: The module should display your sheet name and show column headers like Email, First Name, Last Name in the preview.
⚠
Common mistake β€” If your sheet has merged cells or complex formatting, create a clean copy with simple headers
Make
+
click +
search apps
Google Sheets
GO
Google Sheets
Configure Google Sheets Trig…
Google Sheets
GO
module added
4

Scenario > Add Module > HubSpot > List Contacts

Add HubSpot Connection

Connect to HubSpot so Make can fetch your existing contact database for comparison. This requires a HubSpot account with contacts access.

  1. 1Click the + button to add a new module
  2. 2Search for 'HubSpot' and select it
  3. 3Choose 'List Contacts' from the actions
  4. 4Click 'Create a connection' and enter your HubSpot API key
βœ“ What you should see: HubSpot module appears connected with 'List Contacts' action selected and your API key validated.
⚠
Common mistake β€” Use a private app token, not a legacy API key - legacy keys get deprecated
5

HubSpot Module > List Contacts Configuration

Configure HubSpot Contact Fetch

Set up HubSpot to return all contacts with the properties you need for comparison. Limit the fields to avoid unnecessary API calls.

  1. 1Set 'Limit' to 100 (maximum per call)
  2. 2In 'Properties' field, add: email,firstname,lastname,createdate
  3. 3Leave 'Property History' unchecked
  4. 4Set 'Associations' to None
βœ“ What you should see: The module shows it will fetch 100 contacts per execution with email, firstname, lastname, and createdate fields.
⚠
Common mistake β€” Don't fetch all properties - HubSpot charges extra API calls for unnecessary custom fields
6

Tools > Array Aggregator

Add Array Aggregator

Collect all HubSpot contacts into a single array so you can compare against your Google Sheets list efficiently.

  1. 1Add a new module after HubSpot
  2. 2Search for 'Array aggregator' in Tools
  3. 3Select 'Array aggregator'
  4. 4Set 'Source module' to the HubSpot List Contacts module
βœ“ What you should see: Array aggregator module appears with HubSpot selected as the source, showing it will collect contact arrays.
7

Flow Control > Iterator

Add Iterator for Sheet Rows

Create an iterator to loop through each row in your Google Sheets contact list for individual comparison against HubSpot data.

  1. 1Add a new module after the Array aggregator
  2. 2Search for 'Iterator' in Flow Control
  3. 3Select 'Iterator'
  4. 4Map the 'Array' field to the Google Sheets rows output
βœ“ What you should see: Iterator module shows it will process each Google Sheets row individually for comparison logic.
⚠
Common mistake β€” Don't iterate over the HubSpot array - that creates nested loops and burns operations
8

Iterator > Filter > Condition

Add Filter for Missing Contacts

Create a filter that identifies Google Sheets contacts missing from HubSpot by comparing email addresses between both lists.

  1. 1Click the wrench icon between Iterator and next module
  2. 2Select 'Set up a filter'
  3. 3Set condition: HubSpot contacts array 'does not contain' current Google Sheets email
  4. 4Name the filter 'Missing from HubSpot'
βœ“ What you should see: Filter shows condition checking if current sheet email exists in the HubSpot contacts array.
⚠
Common mistake β€” Use email for matching, not names - names have too many variations and formatting differences
Google Sheets
GO
trigger
filter
Condition
matches criteria?
yes β€” passes through
no β€” skipped
HubSpot
HU
notified
9

HubSpot > Create a Contact

Create HubSpot Contact for Missing Records

Add missing Google Sheets contacts to HubSpot when the filter identifies them as absent from your CRM.

  1. 1Add 'HubSpot' module after the filter
  2. 2Select 'Create a Contact' action
  3. 3Map 'Email' to the Google Sheets email column
  4. 4Map 'First Name' and 'Last Name' to respective sheet columns
βœ“ What you should see: HubSpot Create Contact module shows field mappings from your Google Sheets columns to HubSpot contact properties.
⚠
Common mistake β€” Check HubSpot's duplicate settings - if set to 'reject duplicates', this will fail on existing contacts
10

Array Aggregator > Add Route > Iterator

Add Reverse Comparison Branch

Create a parallel branch to find HubSpot contacts missing from your Google Sheets by iterating through the HubSpot array.

  1. 1Right-click the Array aggregator module
  2. 2Select 'Add another route'
  3. 3Add an Iterator module to this new branch
  4. 4Set Iterator array to the HubSpot contacts from Array aggregator
βœ“ What you should see: Second branch appears with Iterator processing HubSpot contacts, parallel to your Google Sheets processing branch.
⚠
Common mistake β€” This creates a second execution path - make sure both branches have different purposes to avoid conflicts
11

HubSpot Iterator > Filter

Filter HubSpot Contacts Missing from Sheets

Add a filter on the HubSpot branch to identify CRM contacts that don't exist in your Google Sheets list.

  1. 1Add a filter after the HubSpot Iterator
  2. 2Set condition: Google Sheets email column 'does not contain' current HubSpot email
  3. 3Name filter 'Missing from Sheets'
  4. 4Use the 'map' function to create an array of sheet emails for comparison
βœ“ What you should see: Filter compares each HubSpot contact email against the full Google Sheets email list to find missing records.
⚠
Common mistake β€” The 'contains' operator is case-sensitive - use 'lower()' function on both sides if emails have mixed case
12

Google Sheets > Add a Row

Log Missing Contacts to New Sheet

Create a Google Sheets action to log contacts found in HubSpot but missing from your original sheet for review.

  1. 1Add Google Sheets module after the HubSpot filter
  2. 2Select 'Add a Row' action
  3. 3Create or select a 'Missing Contacts Log' spreadsheet
  4. 4Map HubSpot email, firstname, lastname to new sheet columns
βœ“ What you should see: Google Sheets module configured to write missing HubSpot contacts to a separate tracking spreadsheet.
⚠
Common mistake β€” Don't write back to the original sheet - that triggers the scenario again and creates an infinite loop

Drop this into a Make custom function.

Copy this template{{lower(trim(1.email))}} = {{lower(trim(2.properties.email))}}
β–Έ Show code
{{lower(trim(1.email))}} = {{lower(trim(2.properties.email))}}

... expand to see full code

{{lower(trim(1.email))}} = {{lower(trim(2.properties.email))}}

Scaling Beyond 500+ contacts per system+ Records

If your volume exceeds 500+ contacts per system records, apply these adjustments.

1

Batch HubSpot API Calls

Use Make's repeater module to fetch contacts in 100-record chunks rather than individual calls. This reduces API operations from 500 to 5 for a full contact list pull.

2

Implement Progressive Sync

Add a 'Last Modified' date filter so you only reconcile contacts updated since the last run. This cuts operations by 80-90% after initial sync and prevents unnecessary API calls.

3

Split Large Sheets

Break sheets over 1000 rows into separate tabs or files. Google Sheets API performance degrades significantly above 1000 rows and Make's processing time increases exponentially.

Going live

Production Checklist

Before you turn this on for real, confirm each item.

Troubleshooting

Common errors and how to fix them.

Frequently Asked Questions

Common questions about this workflow.

Analysis

VerdictWhy Make for this workflow

Use Make for this if you need bidirectional reconciliation and have over 200 contacts to compare. Make's array aggregator and dual-path routing handles the complex logic better than simple trigger-based platforms. The visual scenario builder makes it easy to debug mismatched records and add custom comparison logic. Skip Make and use Zapier if you only need one-way sync from Sheets to HubSpot - Zapier's HubSpot integration handles basic duplicate detection automatically.

Cost

This workflow uses about 4 operations per Google Sheets row plus 1 operation per 100 HubSpot contacts fetched. For 500 contacts in each system, expect 25 operations per run. Running daily, that's 750 operations monthly, fitting Make's Core plan at $10.59/month. Zapier would need the Professional plan at $49/month for the same volume since it lacks batch processing. Make saves you $460 annually on this workflow.

Tradeoffs

Zapier beats Make on built-in duplicate detection - their HubSpot integration automatically prevents duplicate contact creation without custom filters. N8n offers better bulk operations with their batch processing node, handling 1000+ contacts more efficiently than Make's 100-record API limits. But Make wins on visual debugging and error handling. When your comparison logic fails, Make's execution history shows exactly which records didn't match and why.

You'll hit three main issues after setup. HubSpot's API paginates at 100 contacts maximum per call - if you have 500+ contacts, you need Make's repeater module to fetch all pages. Google Sheets rate limits at 100 requests per 100 seconds, so large reconciliations need delay modules between operations. Email formatting breaks everything - '[email protected]' doesn't match '[email protected]', so wrap all email comparisons in lower() and trim() functions to avoid false mismatches.

Ideas for what to build next

  • β†’
    Add Contact Scoring Sync β€” Create a follow-up scenario that syncs lead scores from your Google Sheets analysis back to HubSpot contact properties for better sales prioritization.
  • β†’
    Set Up Duplicate Merge Notifications β€” Build a Slack notification workflow that alerts your sales team when the reconciliation finds potential duplicate contacts that need manual review and merging.
  • β†’
    Create Contact Activity Timeline β€” Develop a scenario that logs all contact reconciliation changes to a master Google Sheets timeline for audit purposes and data governance compliance.

Related guides

Was this guide helpful?
← Google Sheets + HubSpot overviewMake profile β†’