Google Maps lists the local businesses you want to pitch. Google Sheets is where most small teams already sort, share and track their work.
Moving Google Maps leads to Google Sheets is easy to start but harder to do well, because Maps leaves out the fields you need most for outreach. This guide compares the three routes that work, then shows you how to set up the sheet as a real outreach tracker.
What you can and can't get from Google Maps into a sheet
Every route below pulls from the same public listing data. A Google Business Profile usually gives you:

- Business name and category
- Street address, city and postal code
- Phone number
- Website URL
- Star rating and review count
- Opening hours
- The Maps URL, place ID and coordinates
Some fields are missing from the listing:
- Email addresses. Google doesn't show them on Maps listings.
- Owner or manager names. The listing names the business, not the person who approves spending.
- Social profiles. A few listings link them, but most don't.
There's also a limit on volume. A single Maps search shows only around 120 results, however many businesses match. A search for "dentists in Texas" returns a small fraction of the real list.
The fix is to split searches by city, ZIP code or neighborhood. Why Google Maps stops at about 120 results explains how.
Whichever option you pick, plan for two extra jobs:
- Running many small searches instead of one big one
- Adding emails and names from each business's website
Option 1: Google Sheets add-ons and their daily limits
The fastest way to export Google Maps results to Sheets is an add-on from the Google Workspace Marketplace. You install it and open the sidebar. Then you type a keyword and a location, and rows appear in the active tab.
Setup takes about five minutes. You don't need an API key, a billing account or any code.
The catch is the daily cap. Free tiers work like trials, and at least one popular add-on advertises up to 100 free leads a day. Paid tiers raise the cap and are usually priced per month or per batch of rows. As long as you stay under the cap, this is the closest you'll get to free Google Maps lead generation.
Check these four things before you install one:
- Row limits. Look at the daily or monthly limit on both the free and paid plans.
- Fields it fills. Many add-ons return only listing data. Emails and socials are often a paid extra or missing entirely.
- Permissions. Add-ons ask for access to your spreadsheets. Read what you're granting, especially on a client's Drive.
- Duplicate handling. Two overlapping searches often add the same business twice.
Best for: testing a niche with 50 to 100 leads before you commit to anything bigger.
Option 2: An n8n or Google Places API workflow, with the real setup and API costs
If you want control and can handle some technical work, call the Google Places API yourself and write the results into a sheet. n8n is a popular way to connect the Google Places API to Google Sheets without much code. Google Apps Script also works if you're comfortable with JavaScript.
The setup, step by step
- Create a Google Cloud project, enable the Places API and attach a billing account. Google requires billing even if you stay inside the free allowance.
- Create an API key and restrict it to the Places API. That way, a leaked key can't be used for other Google services.
- In your sheet, add a tab listing the areas you want to cover, with one ZIP code, town or neighborhood per row.
- In n8n, connect Google Sheets with OAuth, read the areas tab and loop through each row.
- For each area, call Text Search with a query like "plumber in 78701". Use a field mask to request only the fields you need.
- Follow the next-page token to collect more results. Text Search returns 20 results per page and stops at 60 per query, which is another reason to search small areas.
- Append each result to a leads tab, using the place ID as the unique key.
- If you need emails, add a step that fetches each website and pulls addresses from it. The API doesn't return emails.
If you've used n8n before, plan on an afternoon. If you haven't, plan on a day or two. Pagination, error handling and the email step take up most of that time.
What it costs
Google bills the Places API per request, and the price depends on which fields you request:
- Cheaper tier: basic fields such as name and address.
- More expensive tiers: phone numbers, websites, ratings and hours.
Google changed its free monthly allowance in 2025. Check the current Maps Platform pricing page instead of trusting an older tutorial.
You'll also pay for an n8n cloud plan, or for hosting if you run n8n yourself.
Two more limits apply:
- No emails or owner names. The API returns the same listing data you see on Maps.
- Storage rules. Google Maps Platform terms restrict how long you can keep some of the returned content. Read them before you treat the sheet as a permanent database.
Best for: technical users who want an automated feed and don't mind maintaining it.
Option 3: Scrape with a lead tool, then import the CSV into Sheets
The third route uses a dedicated tool to collect the data instead of the sheet. You run the search in a Google Maps leads extractor and let it enrich each business. Then you export a CSV and import it into Google Sheets.
GetClient is one example. You search Google Maps by keyword and location. Each lead comes back with its listing data plus the emails, owner's name, phone numbers and social profiles found on the business's website.
Plans start at $9 a month for 3,000 credits. Each lead costs 1 credit, which works out to $0.003 per lead. New accounts get 100 free credits, so you can test a niche first.
Importing the CSV cleanly
- In Google Sheets, go to File > Import > Upload and pick the CSV.
- Choose Insert new sheet for a fresh batch. Choose Append to current sheet only if the columns match your tracker exactly.
- Untick "Convert text to numbers, dates, and formulas" so phone numbers keep their leading plus signs and zeros.
- Check that names with accents display correctly. If they don't, the file wasn't saved as UTF-8.
- Run your duplicate check (covered below) before you do anything else with the rows.
Best for: anyone who needs emails and owner names in the sheet, not just phone numbers and addresses.
Google Maps leads to Google Sheets: the three routes side by side
| Sheets add-on | n8n / Places API | Lead tool + CSV | |
|---|---|---|---|
| Setup time | Minutes | Hours to days | Minutes |
| Cost per lead | Free up to the cap, then by plan | Per-request API pricing plus hosting | $0.003 on GetClient's $9 plan |
| Row limits | Daily cap on free tiers | 60 per query, so split by area | Your credit balance |
| Emails | Often missing or a paid extra | Not included; you build the step | Included from website enrichment |
| Owner names | Rarely | No | Included where found |
If you're doing Google Maps lead generation with Google Sheets for the first time, start with whichever route matches your skills. You can switch later, because the tracker setup below works with all three.
Adding the missing emails, owner names and socials to each row
If your rows came from an add-on or the API, the contact columns will be mostly empty. Fill them by hand in this order, starting with the sources that pay off most:
- Contact page and footer. Most small businesses list an email here. If both a named address and info@ appear, use the named one.
- About or Team page. Local business owners often introduce themselves by name here.
- Social profiles. The website's header or footer usually links to Facebook, Instagram or LinkedIn. Paste each profile URL into its own column.
- Other sources for the owner's name. Try the About section of the Facebook page, Google review replies signed by the owner, and state business registries. This guide to finding business owner names goes deeper.
Add an Email source column with values like contact page, footer, guessed or tool. It shows you which addresses need extra caution.
You can also try IMPORTXML to pull mailto links straight into the sheet:
=IMPORTXML(E2, "//a[starts-with(@href,'mailto:')]/@href")
It works on simple sites but fails on many others, especially sites built with JavaScript. It also slows the sheet down once you have a few hundred rows. Use it as a shortcut for small batches, not as a system.
If filling these columns by hand takes too long for the volume you need, that's the main reason to use option 3.
Setting up the sheet columns for deduping, filtering and status tracking
A good Google Sheets lead tracker has one row per business. Its columns answer three questions: who is this, can we reach them, and where are we with them?
Suggested columns
- A: Business name
- B: Category
- C: City
- D: Phone
- E: Website
- F: Email
- G: Owner first name
- H: Owner last name
- I: Rating
- J: Review count
- K: Socials
- L: Place ID or Maps URL
- M: Domain (formula)
- N: Duplicate flag (formula)
- O: Verification result
- P: Status
- Q: Assigned teammate
- R: Last touch date
- S: Notes
Formulas that keep the list clean
Pull a clean domain from each website. This makes "https://www.joesplumbing.com/contact" and "joesplumbing.com" match:
=IFERROR(LOWER(REGEXEXTRACT(E2, "^(?:https?://)?(?:www[.])?([^/?#:]+)")), "")
Next, flag repeats. This formula marks only the second and later copies, so the first one stays:
=IF(M2="", "", COUNTIF($M$2:M2, M2)>1)
For businesses without a website, check for duplicates by phone number instead. First strip the number down to digits with =REGEXREPLACE(D2, "[^0-9]", "").
Filter column N to TRUE and delete those rows. How to dedupe a lead list covers edge cases, such as chains whose locations share one domain.
Status tracking
Select column P, go to Data > Data validation and add a dropdown with these fixed values:
- New
- Verified
- Queued
- Sent
- Replied
- Interested
- Not interested
- Bounced
- Do not contact
Fixed values matter. Free-typed statuses like "replied!!" or "Replied - call back" break every filter you build later.
Then add a few more pieces:
- Filter views (Data > Filter views). Each teammate can see only their own rows without changing what others see.
- Conditional formatting. Color Interested rows green and Do not contact rows grey.
- A protected range on the formula columns, so nobody types over them.
- A Summary tab with counts for each status, using formulas like
=COUNTIF(Leads!P:P, "Replied").
Verifying emails in the sheet before anyone sends
Emails scraped from websites go out of date. Staff leave, domains lapse and contact forms replace old addresses.
Sending to dead addresses raises your bounce rate. A high bounce rate tells inbox providers that you don't check who you're emailing, and that can push your messages toward spam.
Run every address through a verifier and record the result in column O. Most verifiers sort addresses into four groups:
- Valid: the mailbox exists. Send.
- Invalid: the mailbox doesn't exist. Remove the row or set its status to Do not contact.
- Catch-all: the domain accepts every address, so the check can't confirm this one. Decide case by case; this guide on catch-all emails explains the tradeoff.
- Unknown: the mail server didn't answer. Retry later or skip it.
GetClient's built-in verification costs 1 credit per email, from the same balance you use for leads. Checking 500 addresses uses 500 credits.
Whatever tool you use, filter the sheet to Valid before you export a send list. Verify your email list before sending explains the reasons in more detail.
When to move from Sheets to a cold email tool, and how to make the switch
Sheets is a fine place to build and sort a list, but a poor place to send from. You've outgrown it when any of these happen:
- You're copying rows into a mail merge add-on and hitting its daily cap.
- Follow-ups only happen if someone remembers to check the Last touch column.
- Replies are spread across several inboxes, and nobody knows who answered what.
- You want to send from more than one mailbox to stay under each one's daily limit.
- Two people edit statuses at the same time and overwrite each other's changes.
How to switch without losing work
- Freeze the sheet. Ask the team to stop editing for an hour.
- Filter to rows you can send to. Keep rows where Verification is Valid (plus any catch-alls you chose to keep) and Status is New or Verified.
- Rename headers to match the merge tags in your sending tool, such as first_name, company and city. Lowercase with underscores is the safest format.
- Handle missing first names. Either set a fallback like "there" in the tool, or move those rows into a separate campaign that doesn't use a name.
- Download as CSV (File > Download > Comma-separated values) and import the file into the sending tool. Check the field mapping screen before you confirm.
- Mark the exported rows as Queued in the sheet, so nobody adds them to a second campaign.
- Keep the sheet as your record of who you've contacted. Copy Do not contact rows to a suppression tab, and check it before every new import.
If your leads already live in GetClient, you can skip the export step. Connect your own Gmail, Outlook or SMTP mailboxes and send campaigns and follow-ups with no sending fees. There's no limit on campaigns or mailboxes, and every reply arrives in one inbox.
If your team works in GoHighLevel or Instantly, you can push the list there directly instead. Either way, credits only pay for leads and verification; see pricing.
Next steps
- Pick one niche and one city, then run a test of 50 to 100 leads using the route that fits your skills.
- Set up the tracker columns and duplicate formulas before you import anything.
- Fill in the email and owner name columns, then verify every address.
- Send to the verified rows. Move to a sending tool once follow-ups and replies get hard to track in the sheet.
