# Google Maps Scraper — 12 Fields, Cross-Run Dedupe, No Login (`themineworks/google-maps-search-scraper`) Actor

Scrape Google Maps business listings by search query: name, category, address, phone, website, rating, review count, hours, coordinates. No login, no email guessing. Pay only per place delivered. Works in Claude, ChatGPT & any MCP agent.

- **URL**: https://apify.com/themineworks/google-maps-search-scraper.md
- **Developed by:** [The Mine Works](https://apify.com/themineworks) (community)
- **Categories:** Lead generation, Business, MCP servers
- **Stats:** 1 total users, 0 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $0.90 / 1,000 place scrapeds

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

Learn more: https://docs.apify.com/platform/actors/running/actors-in-store#pay-per-event

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.
Actors are written with capital "A".

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## 📍 Google Maps Search Scraper: Business Listings, No Login

### Overview

Google Maps Search Scraper turns any Google Maps search ("coffee shops in Austin TX", "plumbers in Chicago", "dentists in Mumbai") into a clean list of business listings. Each record carries name, category, address, phone, website, rating, review count, opening hours, and coordinates, straight from what Google Maps itself shows. No email guessing, no MX verification, no website crawling, no Google account, no login, no API key.

This is the plain, bare version of Maps scraping: search in, business listings out. If you need verified emails on top of the listing data, use [Google Maps Leads Scraper](https://apify.com/themineworks/maps-leads) instead. This actor is the cheaper, faster option when you just need the listings themselves.

```json
{
  "name": "Mozart's Coffee Roasters",
  "address": "3825 Lake Austin Blvd, Austin, TX 78703",
  "phone": "(512) 477-2900",
  "website": "https://mozartscoffee.com",
  "rating": 4.5,
  "review_count": 10743,
  "opening_hours": {
    "Tuesday": "7 AM-12 AM",
    "Wednesday": "7 AM-12 AM",
    "Thursday": "7 AM-12 AM",
    "Friday": "7 AM-12 AM",
    "Saturday": "7 AM-12 AM",
    "Sunday": "7 AM-12 AM",
    "Monday": "7 AM-12 AM"
  },
  "latitude": 30.2954696,
  "longitude": -97.7839512,
  "google_maps_url": "https://www.google.com/maps/place/Mozart's+Coffee+Roasters/@30.2954696,-97.7839512,17z/data=!3m1!4b1!4m6!3m5!1s0x8644b5554461664d:0xbc4ff333ec9ad1ad!8m2!3d30.2954696!4d-97.7839512!16s%2Fm%2F020z4hc",
  "business_status": "OPERATIONAL",
  "query_used": "coffee shops in Austin, TX",
  "charged": true,
  "scraped_at": "2026-07-15T01:58:49.938Z"
}
```

This is a real record captured on a live QA run, not a placeholder. The `charged` flag is shown as it reads under current billing: every listing delivered to your dataset is charged.

✅ No login required | ✅ No API key | ✅ No email guessing, pure listing data | ✅ MCP-ready for AI agents

### Features

Beyond the 120-results ceiling. Drives Google Maps like a person, so you go past the map's per-area cap.
Bulk queries in one run. Pass a single query and location, or a list of full search strings for bulk runs.
Full listing coverage. Name, category, address, phone, website, rating, reviews, hours, and coordinates.
Cross-run deduplication. Businesses seen in a previous run are skipped automatically.
Residential proxy by default, pinned to the US to avoid Google's EU consent interstitial.

### How it works

The official Google Places API caps search results and Google Maps itself will only display about 120 places per area. This scraper drives Google Maps the way a person would: it searches, scrolls the results feed to load more cards past the fold, then opens each place page and reads the same fields a visitor sees. There is no email-finding step and no website crawl, which is what keeps this actor cheap and fast next to a full lead-enrichment scraper.

Every field is read straight from the rendered Google Maps DOM. Business status is read from the "permanently closed" banner when present; when the banner selector cannot confirm a closure, the actor reports the business as operational rather than guessing closed, since a false "closed" would silently hide a real business from your results.

### 🧾 Input configuration

```json
{
  "query": "coffee shops",
  "location": "Austin, TX",
  "maxResults": 5,
  "skipClosedBusinesses": true,
  "deduplicateAcrossRuns": true,
  "proxyConfig": { "useApifyProxy": true, "apifyProxyGroups": ["RESIDENTIAL"], "apifyProxyCountry": "US" }
}
```

For bulk runs, replace `query` + `location` with a `searchQueries` array, e.g. `["plumbers in Chicago", "dentists in Mumbai"]`.

### 📤 Output format

```json
{
  "name": "Mozart's Coffee Roasters",
  "address": "3825 Lake Austin Blvd, Austin, TX 78703",
  "phone": "(512) 477-2900",
  "website": "https://mozartscoffee.com",
  "rating": 4.5,
  "review_count": 10743,
  "opening_hours": { "Monday": "7 AM-12 AM" },
  "latitude": 30.2954696,
  "longitude": -97.7839512,
  "google_maps_url": "https://www.google.com/maps/place/Mozart's+Coffee+Roasters/...",
  "business_status": "OPERATIONAL",
  "query_used": "coffee shops in Austin, TX",
  "charged": true,
  "scraped_at": "2026-07-15T01:58:49.938Z"
}
```

Every listing record contains these fields:

| Field | Description |
| --- | --- |
| 🏢 `name` | Business name |
| 🏷️ `category` | Business category, when Google Maps exposes it on the place page |
| 📍 `address` | Full address |
| 📞 `phone` | Phone number |
| 🌐 `website` | Business website URL |
| ⭐ `rating` | Google Maps star rating |
| 💬 `review_count` | Number of Google Maps reviews |
| 🕒 `opening_hours` | Business hours by day |
| 🗺️ `latitude` / `longitude` | Coordinates |
| 🔗 `google_maps_url` | Canonical Google Maps place URL |
| 🚦 `business_status` | `OPERATIONAL` / `CLOSED_PERMANENTLY` / etc. |
| 🔎 `query_used` | Search query that returned this business |
| 💳 `charged` | Whether this result was billed via PPE |
| 🆔 `place_id` | Google Maps place ID (used for cross-run dedup) |
| 🕰️ `scraped_at` | ISO 8601 timestamp |

### 💼 Common use cases

**Market mapping and territory research**
Pull every business in a category and city to size a market or plan sales territories.
Compare listing density and rating spread across neighborhoods.

**Local marketing and agency prospecting**
Build a raw list of local businesses in a niche before deciding who's worth enriching further.
Hand qualified subsets to [Google Maps Leads Scraper](https://apify.com/themineworks/maps-leads) once you know who to email.

**Directory and app data**
Populate a local directory, map overlay, or comparison app with live business listings.
Keep name, address, phone, and hours current with scheduled re-runs.

**Competitive and reputation tracking**
Track rating and review-count trends for competitors in a category over time.
Feed `google_maps_url` values straight into [Google Maps Reviews Scraper](https://apify.com/themineworks/google-maps-reviews) for a deeper read.

### 🚀 Getting started

1. Open the actor and enter a search query (e.g. `coffee shops`) and a location (e.g. `Austin, TX`), or switch to `searchQueries` for a bulk list of full search strings.
2. Set `maxResults` per query (default 5) to control volume and cost.
3. Leave `skipClosedBusinesses` on so permanently closed listings never cost you a result.
4. Keep `deduplicateAcrossRuns` on to avoid paying for the same business twice across runs.
5. Click Start, then download the dataset as JSON, CSV, or Excel, or pull it via API or MCP.

### FAQ

**How do you go past Google's 120-results ceiling?**
A plain Google Maps search only exposes about 120 places before the scroll ends. This scraper runs each query as its own search and drives the map like a real user, so across queries you can pull far more than a single map screen would show. Use several distinct, local queries for the widest coverage.

**When am I charged?**
Per business listing successfully delivered, at the `place-scraped` event. There is no free tier. Permanently closed businesses (when `skipClosedBusinesses` is on), extraction failures, and businesses already seen in a previous run (when `deduplicateAcrossRuns` is on) are never charged. Blocked and empty runs are never charged either: you only pay for a listing that actually reaches your dataset.

**Does this actor find email addresses?**
No, by design. This is the plain, bare listing scraper; it never visits a business's own website and never guesses or verifies emails. For verified emails on top of the same listing fields, use [Google Maps Leads Scraper](https://apify.com/themineworks/maps-leads).

**Does it need a login or API key?**
No. It reads only public Google Maps data through Apify's residential proxy. No Google account, no cookies, no third-party data API.

**Can I use it inside an AI agent?**
Yes. It is exposed as an MCP tool. See below.

### Use in Claude, ChatGPT & any MCP agent

```
https://mcp.apify.com/?tools=themineworks/google-maps-search-scraper
```

Or call it programmatically with the Apify client:

```js
import { ApifyClient } from 'apify-client';

const client = new ApifyClient({ token: 'YOUR_APIFY_TOKEN' });

const run = await client.actor('themineworks/google-maps-search-scraper').call({
  query: 'coffee shops',
  location: 'Austin, TX',
  maxResults: 5,
});

const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(items.filter((i) => !i._type));
```

### 🛠️ Complete your Google Maps pipeline

This actor is the entry point to a full Google Maps and lead-gen suite:

- **[Google Maps Leads Scraper](https://apify.com/themineworks/maps-leads)**: the same search, plus MX-verified email addresses. Pay only for leads with a confirmed email.
- **[Google Maps Reviews Scraper](https://apify.com/themineworks/google-maps-reviews)**: pull ratings, full review text, and owner replies for any business you found here.

Typical flow: google-maps-search-scraper finds the businesses, maps-leads adds verified emails for outbound, google-maps-reviews pulls reviews for reputation and market research on the same businesses.

### Your feedback

Found a field that doesn't match what Google Maps shows, or want a field added? Reach out through the Apify profile. Bug reports with a query and location that reproduce the issue get fixed fastest.

# Actor input Schema

## `query` (type: `string`):

What to search for on Google Maps, e.g. "coffee shops" or "plumbers". Combined with Location below into one search. Leave empty if you provide Search Queries (bulk) instead.

## `location` (type: `string`):

City, region, or area to search in, e.g. "Austin, TX". Appended to Search Query as "{query} in {location}". Leave empty to search Query as-is.

## `searchQueries` (type: `array`):

Optional list of full Google Maps search strings for bulk runs, e.g. \["plumbers in Chicago", "dentists in Mumbai"]. Overrides Search Query + Location when provided. Each string becomes an independent search.

## `maxResults` (type: `integer`):

Maximum number of place results to extract per query.

## `language` (type: `string`):

Google Maps interface language code (BCP-47). Affects category names and hours labels.

## `skipClosedBusinesses` (type: `boolean`):

When true, businesses marked CLOSED\_PERMANENTLY are skipped and never charged. They still appear in output with charged:false.

## `deduplicateAcrossRuns` (type: `boolean`):

When true, stores processed Google Maps place\_ids in a named Key-Value store ('google-maps-search-scraper-seen'). Places seen in previous runs are skipped. Resets only when you manually clear that store.

## `proxyConfig` (type: `object`):

Apify proxy. Defaults to datacenter — the Maps search endpoint is public and needs no residential. Override only if blocked.

## Actor input object example

```json
{
  "query": "coffee shops",
  "location": "Austin, TX",
  "maxResults": 5,
  "language": "en",
  "skipClosedBusinesses": true,
  "deduplicateAcrossRuns": true,
  "proxyConfig": {
    "useApifyProxy": true
  }
}
```

# Actor output Schema

## `results` (type: `string`):

No description

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "query": "coffee shops",
    "location": "Austin, TX",
    "maxResults": 5,
    "proxyConfig": {
        "useApifyProxy": true
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("themineworks/google-maps-search-scraper").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "query": "coffee shops",
    "location": "Austin, TX",
    "maxResults": 5,
    "proxyConfig": { "useApifyProxy": True },
}

# Run the Actor and wait for it to finish
run = client.actor("themineworks/google-maps-search-scraper").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print("💾 Check your data here: https://console.apify.com/storage/datasets/" + run["defaultDatasetId"])
for item in client.dataset(run["defaultDatasetId"]).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "query": "coffee shops",
  "location": "Austin, TX",
  "maxResults": 5,
  "proxyConfig": {
    "useApifyProxy": true
  }
}' |
apify call themineworks/google-maps-search-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "command": "npx",
            "args": [
                "mcp-remote",
                "https://mcp.apify.com/?tools=themineworks/google-maps-search-scraper",
                "--header",
                "Authorization: Bearer <YOUR_API_TOKEN>"
            ]
        }
    }
}

```

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/UshhHseNvkTgvudcB/builds/xCgBvrBNwCOUuAVL6/openapi.json
