Intermediate~15 min setupProductivity & CRMVerified April 2026
Google Sheets logo
HubSpot logo

How to Export HubSpot Contacts to Google Sheets with Power Automate

Automatically export HubSpot contacts matching specific criteria to a Google Sheet on a scheduled basis.

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

Best for

Teams that need regular contact exports for reporting without custom development.

Not ideal for

Teams needing real-time sync or handling 10,000+ contacts daily should use direct API integration.

Sync type

scheduled

Use case type

reporting

Real-World Example

💡

A 25-person marketing agency exports all HubSpot contacts with 'Customer' lifecycle stage to Google Sheets every Monday at 9 AM. The sheet feeds their monthly retention analysis dashboard. Before automation, an analyst spent 45 minutes each week manually exporting and formatting the data.

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 Power Automate

Copy the pre-built Power Automate blueprint and paste it straight into Power Automate. 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.

HubSpot account with Contacts read permissions
Google account with Google Sheets access
Existing Google Sheet with headers formatted as a table
Power Automate license (Office 365 or standalone)

Optional

Admin access to grant connector permissions in your tenant

Field Mapping

Map these fields between your apps.

FieldAPI Name
Required
Contact IDid
Emailemail
6 optional fields▸ show
First Namefirstname
Last Namelastname
Companycompany
Lifecycle Stagelifecyclestage
Create Datecreatedate
Last Modifiedlastmodifieddate

Step-by-Step Setup

1

My flows > New flow > Scheduled cloud flow

Create a new scheduled flow

Go to make.powerautomate.com and click 'My flows' in the left sidebar. Click 'New flow' then select 'Scheduled cloud flow'. Name it 'HubSpot Contact Export' and set the recurrence to daily, weekly, or monthly based on your needs. Choose your start date and time.

  1. 1Click 'My flows' in the left sidebar
  2. 2Click the blue 'New flow' button
  3. 3Select 'Scheduled cloud flow'
  4. 4Enter flow name: 'HubSpot Contact Export'
  5. 5Set recurrence interval and start time
What you should see: You should see the flow designer with a 'Recurrence' trigger already configured.
Common mistake — Power Automate runs on UTC time by default. Adjust for your timezone in the recurrence settings.
2

Flow designer > New step > Search connectors

Add HubSpot connection

Click 'New step' and search for 'HubSpot'. Select the HubSpot connector, then choose 'List contacts' action. You'll need to authenticate with your HubSpot account. Power Automate will redirect you to HubSpot's login page.

  1. 1Click 'New step' below the recurrence trigger
  2. 2Type 'HubSpot' in the search box
  3. 3Select the HubSpot connector
  4. 4Choose 'List contacts' action
  5. 5Click 'Sign in' and complete HubSpot authentication
What you should see: You should see 'List contacts' step with a green checkmark indicating successful connection.
Common mistake — Your HubSpot user needs 'Contacts: Read' permissions. Contact your HubSpot admin if authentication fails.
3

HubSpot List contacts action > Parameters

Configure contact filters

In the 'List contacts' step, set the 'Count' field to control how many contacts to retrieve (max 100 per call). Add property names you want to export in the 'Properties' field - use HubSpot internal property names separated by commas. Leave other fields blank unless you need specific filtering.

  1. 1Set Count to 100 (or desired batch size)
  2. 2In Properties field, enter: firstname,lastname,email,company,lifecyclestage
  3. 3Leave Archived and Search blank
  4. 4Expand 'Show advanced options' if needed for date filters
What you should see: The step should show your configured parameters without any red error indicators.
Common mistake — HubSpot property names are case-sensitive. Use 'lifecyclestage' not 'lifecycle_stage' or 'lifeCycleStage'.
Google Sheets
GO
trigger
filter
Condition
matches criteria?
yes — passes through
no — skipped
HubSpot
HU
notified
4

Flow designer > New step > Control > Apply to each

Add apply to each loop

Click 'New step' and search for 'Control'. Select 'Apply to each' action. In the 'Select an output from previous steps' box, choose 'value' from the HubSpot step's dynamic content. This loop will process each contact individually.

  1. 1Click 'New step' below the HubSpot action
  2. 2Search for 'Control' and select it
  3. 3Choose 'Apply to each'
  4. 4Click in the output box
  5. 5Select 'value' from HubSpot dynamic content
What you should see: You should see an 'Apply to each' container with 'value' selected as the input.
5

Apply to each > Add an action > Excel Online > Add a row into a table

Connect to Google Sheets

Inside the 'Apply to each' loop, click 'Add an action'. Search for 'Excel' and you'll see Google Sheets under 'Excel Online (Business)'. Choose 'Add a row into a table' action. Sign in with your Google account when prompted.

  1. 1Click 'Add an action' inside the Apply to each loop
  2. 2Search for 'Excel' in the connector search
  3. 3Select 'Excel Online (Business)' - this covers Google Sheets
  4. 4Choose 'Add a row into a table'
  5. 5Authenticate with your Google account
What you should see: The Google Sheets action appears inside your loop with connection established.
Common mistake — Power Automate calls Google Sheets 'Excel Online (Business)' which is confusing but correct.
6

Add a row into a table > Location/File/Table dropdowns

Select target spreadsheet and worksheet

In the 'Add a row into a table' action, click the Location dropdown and select 'GoogleDrive'. Choose your target spreadsheet from the File dropdown - you can browse or type the name. Select the specific worksheet tab from the Table dropdown. The sheet must already exist with headers.

  1. 1Set Location to 'GoogleDrive'
  2. 2Click File dropdown and select your target spreadsheet
  3. 3Choose the worksheet tab from Table dropdown
  4. 4Verify the table headers are detected correctly
What you should see: You should see your spreadsheet columns listed as input fields in the action.
Common mistake — Your Google Sheet needs a proper table with headers in row 1. Power Automate won't detect unformatted ranges.
7

Add a row into a table > Column input fields > Dynamic content

Map HubSpot fields to sheet columns

For each column in your Google Sheet, click the input field and select the corresponding HubSpot property from dynamic content. You'll see properties nested under 'properties' in the dynamic content panel. Map firstname to First Name column, lastname to Last Name, etc.

  1. 1Click in the 'First Name' input field
  2. 2Select 'firstname' from properties dynamic content
  3. 3Click in the 'Last Name' field and select 'lastname'
  4. 4Map 'email', 'company', and other fields to respective columns
  5. 5Use 'id' for the HubSpot Contact ID column if present
What you should see: Each sheet column should show the mapped HubSpot property name in blue dynamic content tags.
Common mistake — Nested properties require two clicks - first expand 'properties' then select the specific field like 'firstname'.
Google Sheets fields
Column A
Column B
Email
Status
Notes
available as variables:
1.props.Column A
1.props.Column B
1.props.Email
1.props.Status
1.props.Notes
8

Apply to each > Add an action > Control > Condition

Add condition for filtering contacts

Above the Google Sheets action but inside the loop, click 'Add an action' and select 'Condition' from Control actions. Set up a filter like lifecycle stage equals 'customer' or created date within the last 30 days. This prevents writing unwanted contacts to your sheet.

  1. 1Click 'Add an action' before the Google Sheets step
  2. 2Search 'Control' and select 'Condition'
  3. 3Choose 'lifecyclestage' from properties dynamic content
  4. 4Set condition to 'is equal to'
  5. 5Type 'customer' or your desired filter value
What you should see: You should see a condition with Yes/No branches, and the Google Sheets action should be in the Yes branch.
Common mistake — HubSpot lifecycle values are lowercase: 'subscriber', 'lead', 'customer', not 'Customer' or 'Lead'.
9

Inside condition Yes branch > Add an action > Excel Online > Get rows

Add duplicate prevention

Before adding the row to Google Sheets, add a 'Get rows' action to check if the contact already exists. Use a filter query with the HubSpot contact ID. Then add another condition - only insert the row if no existing rows were found. This prevents duplicate entries on subsequent runs.

  1. 1Add 'Get rows' action before 'Add a row'
  2. 2Select the same Location, File, and Table
  3. 3In Filter Query, enter: HubSpotID eq 'CONTACT_ID_DYNAMIC_VALUE'
  4. 4Add another condition checking if row count equals 0
  5. 5Move 'Add a row' into this new condition's Yes branch
What you should see: Your flow should only add rows for contacts that don't already exist in the sheet.
Common mistake — Filter queries use OData syntax. String values need single quotes: HubSpotID eq '12345' not HubSpotID eq 12345.
10

Flow designer > Save > Test > Manually

Test and save the flow

Click 'Save' in the top right, then 'Test' to run a test execution. Choose 'Manually' and click 'Test'. The flow will run immediately and show you results for each step. Check your Google Sheet to verify contacts were added correctly with proper field mapping.

  1. 1Click 'Save' button in top toolbar
  2. 2Click 'Test' once saving completes
  3. 3Select 'Manually' test option
  4. 4Click 'Test' button to start execution
  5. 5Monitor each step's execution status
What you should see: All steps should show green checkmarks and your Google Sheet should contain the exported HubSpot contacts.
Common mistake — Test runs count against your Power Automate quotas. Don't test repeatedly with large contact sets.

Use this Power Fx expression in the Filter Query to only export contacts modified in the last 7 days, reducing processing time and focusing on recent changes.

JavaScript — Code Step// In the Get rows Filter Query field, use this expression:
▸ Show code
// In the Get rows Filter Query field, use this expression:
// to only process contacts modified in the last 7 days
lastmodifieddate ge @{formatDateTime(addDays(utcnow(), -7), 'yyyy-MM-dd')}

... expand to see full code

// In the Get rows Filter Query field, use this expression:
// to only process contacts modified in the last 7 days
lastmodifieddate ge @{formatDateTime(addDays(utcnow(), -7), 'yyyy-MM-dd')}

// For lifecycle stage filtering, combine conditions:
lastmodifieddate ge @{formatDateTime(addDays(utcnow(), -7), 'yyyy-MM-dd')} and lifecyclestage eq 'customer'

// To handle date formatting in the sheet, use this in date columns:
formatDateTime(items('Apply_to_each')?['properties']?['createdate'], 'MM/dd/yyyy')
Power Automate
▶ Test flow
executed
Google Sheets
HubSpot
HubSpot
🔔 notification
received

Scaling Beyond 1,000+ contacts per export+ Records

If your volume exceeds 1,000+ contacts per export records, apply these adjustments.

1

Use pagination with after parameter

HubSpot limits responses to 100 contacts max. Use the 'after' parameter from previous responses to fetch subsequent batches across multiple flow runs.

2

Implement batch processing with delay

Add a Delay action between batches to avoid hitting HubSpot's rate limits. Start with 2-second delays and increase if you hit 429 rate limit errors.

3

Switch to bulk CSV export

For 10,000+ contacts, use HubSpot's bulk export API endpoint instead. This requires a custom HTTP action but handles large datasets more efficiently.

4

Monitor Power Automate quotas

Each contact processed counts as an action. 5,000 contacts = 5,000+ actions per run. Consider upgrading your Power Automate plan or splitting across multiple flows.

5

Use incremental exports

Export only contacts modified since last run using lastmodifieddate filters. Store the last export timestamp in a SharePoint list or variable to track progress.

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 n8n for this workflow

Use Power Automate for this if you're already in the Microsoft ecosystem and need scheduled contact exports without custom development. The native Excel Online connector handles Google Sheets surprisingly well, and the visual flow designer makes field mapping obvious for non-technical users. Skip Power Automate if you need real-time sync - the scheduled trigger approach means data can be hours old.

Cost

Real math: Each contact export uses 4-5 actions (HubSpot fetch, condition check, duplicate lookup, sheet write, loop iteration). At 500 contacts monthly, that's 2,500 actions. Power Automate's free tier includes 750 actions/month, so you'll hit the Office 365 plan at $15/month quickly. Make handles 1,000 operations free monthly, making it $180/year cheaper for this volume.

Tradeoffs

Zapier's HubSpot trigger fires faster but costs $20/month minimum and burns through tasks quickly with bulk exports. Make excels at complex field transformations and costs less for high-volume scenarios. n8n gives you unlimited executions if self-hosted but requires server maintenance. Pipedream handles larger batches per run (1,000+ contacts) and includes better error handling. Power Automate wins on enterprise compliance and integration with existing Office 365 workflows.

You'll hit HubSpot's 100 contacts per API call limit immediately - pagination becomes mandatory above small datasets. Power Automate's Apply to each loop processes sequentially, so 1,000 contacts takes 15+ minutes to complete. The Excel Online connector sometimes fails on Google Sheets with complex formatting or merged cells. Watch for the 'properties' nesting issue - firstname is under properties.firstname, not directly accessible, which trips up first-time users consistently.

Ideas for what to build next

  • Add lead score filteringExtend the flow to only export contacts above a certain HubSpot lead score threshold for more targeted reporting.
  • Create reverse sync workflowBuild a companion flow that watches for Google Sheet changes and updates HubSpot contact properties accordingly.
  • Add Slack notificationsInclude a Slack step that posts a summary message with count of contacts exported after each successful run.

Related guides

Was this guide helpful?
Google Sheets + HubSpot overviewPower Automate profile →