# Google Maps Reviews Scraper - Exact Dates, Replies & Photos (`parseforge/google-maps-reviews-scraper`) Actor

Google Maps reviews by place URL, ID or search: exact dates, owner replies, photos, likes, translations. No login. Export CSV, Excel, JSON, XML.

- **URL**: https://apify.com/parseforge/google-maps-reviews-scraper.md
- **Developed by:** [ParseForge](https://apify.com/parseforge) (community)
- **Categories:** Lead generation, Automation, Travel
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $0.53 / 1,000 reviews

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/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
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.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## 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.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

[![ParseForge](https://raw.githubusercontent.com/ParseForge/apify-assets/main/banner-v4.webp)](https://apify.com/parseforge?fpr=vmoqkp)

### Google Maps Reviews Scraper: Google Reviews API with Exact Dates, Owner Replies & Photos

**Export Google Maps reviews for any business from its place URL, place ID, or a search like "pizza in Chicago": 5,000 reviews of one restaurant came back in 87 seconds in our last test.** Every review carries its exact publish date, the reviewer, likes, photos, the owner's reply, Google's translation, the guided answers (price per person, meal type, wait time), and the Food / Service / Atmosphere scores, with the place's name, address, rating and review total on the same row. No login, no Google API key, no browser. Export to CSV, JSON, Excel, or XML.

The official Google Places API returns at most 5 reviews per place. This Actor reads the same review list the Google Maps "All reviews" window shows, page by page, in Google's own sort orders, and hands back one flat row per review with 40 fields.

| Who uses it | What they export Google reviews for |
|---|---|
| Local SEO and reputation agencies | Review monitoring for every client location, new reviews and owner replies on a schedule |
| Multi-location brands | Google business reviews across all branches, compared by rating, topic and reply rate |
| Market researchers | What customers praise and complain about in a category and a city |
| Data scientists | Review text with ratings, languages and translations for sentiment and topic models |
| Lead generation teams | Businesses with low ratings or unanswered reviews, with website and phone on every row |

### What it does

The Actor takes Google Maps place URLs, place IDs (ChIJ...), feature IDs or CIDs, and search terms with a location, alone or together, and returns one row per review.

- ⭐ **Review:** rating, full text, language, Google's translation into your language, exact publish time (ISO 8601) and Google's relative date.
- 👤 **Reviewer:** name, contributor ID and profile URL, photo, total reviews and photos posted, Local Guide flag.
- 🏪 **Owner reply:** the business response text and its date.
- 👍 **Engagement:** likes and all reactions, plus the review's photos.
- 🧾 **Review details:** the guided answers Google asks for (price per person, meal type, wait time, parking, recommended dishes) and the Food, Service and Atmosphere scores.
- 📍 **Place on every row:** name, place ID, feature ID, CID, address, main and all categories, rating, total reviews, coordinates, website and phone.
- 🔎 **Filters:** star ratings, "only reviews newer than" a date, text contains, only reviews with text, only reviews the owner answered.

### What you can do with Google reviews data

**📡 Monitor new reviews on a schedule.**

Run every morning with `sort` set to newest and `reviewsNewerThan` set to "1 day". The run stops reading each place as soon as it reaches older reviews, so a daily check stays small and cheap.

**🚨 Catch bad reviews first.**

Set `starRatings` to 1 and 2 with `sort` "lowestRating" and `onlyWithText` on. The run reads the lowest reviews first and stops each place when the ratings climb out of range.

**🗺️ Benchmark a category in a city.**

Search "dentist" in "Austin, TX" with `maxPlacesPerSearch` 20 and `maxReviewsPerPlace` 200, then compare ratings, reply rates and sub-scores across every practice.

**🌍 Read reviews in any language.**

Set `language` to your language: reviews written in another one come with Google's translation in `textTranslated`, and the original stays in `text`.

### Why choose this scraper

| | What you get |
|---|---|
| **Exact dates** | `publishedAt` is Google's own timestamp to the millisecond, not a guess from "3 weeks ago". |
| **The whole review** | Owner reply, photos, likes, translation, guided answers and sub-ratings, all on the same row. |
| **Place data included** | Name, IDs, address, rating, total reviews, website and phone repeat on every review, so one file is enough. |
| **Any way in** | Place URLs, share links, ChIJ place IDs, feature IDs, CIDs, Maps search URLs, or a search term and a location. |
| **Filters that save money** | Stars, date, text and owner-reply filters run as reviews are read. Only matching reviews are delivered and billed. |
| **Light and fast** | Plain HTTP, no browser: up to 60 reviews per request and about 150 MB of memory for a 5,000-review run. |

### How it compares

All scrapers below read public Google Maps reviews. Prices are each Actor's public Store price for its main result event, read on September 24, 2026, lowest to highest.

| Actor | Price per 1,000 reviews | Runs |
|---|---|---|
| kaix/google-maps-reviews-scraper | $0.04 | 156,169 |
| curious\_coder/google-maps-reviews-scraper | $0.20 | 14,290 |
| solidcode/google-maps-reviews-scraper | $0.25 | 6,077 |
| web\_wanderer/google-reviews-scraper | $0.35 (free tier) to $0.22 | 389,899 |
| compass/Google-Maps-Reviews-Scraper | $0.60 (free tier) to $0.15 | 167,893,844 |
| **ParseForge** | **$0.60 (free tier) to $0.534** | new |

Honest ceiling: Google shows signed-out visitors its review list, not every review ever posted. On a landmark with 112,688 reviews, newest-first reached back one year (3,540 reviews); on a busy deli it reached four months in 2,820 reviews and kept going. Every row carries `placeTotalReviews`, so you always see your coverage.

### What a Google Maps review looks like

One unedited row from a verified run on September 24, 2026:

```json
{
  "imageUrl": "https://lh3.googleusercontent.com/a/ACg8ocJzQH7fx2VaLLQ3hnHSpoqU90iZFahTej5OwYMiP4PEThGQbzM=s64-c-rp-mo-ba12-br100",
  "reviewId": "Ci9DQUlRQUNvZENodHljRjlvT2xGdU5FbHFhMFF5YkhGaU0xTlBjbUU0TWxCWFpFRRAB",
  "reviewUrl": "https://www.google.com/maps/reviews/data=!4m8!14m7!1m6!2m5!1sCi9DQUlRQUNvZENodHljRjlvT2xGdU5FbHFhMFF5YkhGaU0xTlBjbUU0TWxCWFpFRRAB!2m1!1s0x0:0xe494c5a4cb742aeb!3m1!1s2@1:CAIQACodChtycF9oOlFuNElqa0QybHFiM1NPcmE4MlBXZEE%7C%7C?hl=en-US",
  "rating": 5,
  "text": "Excellent service. The wait time for our order was long...but worth the wait. Drinks and food 😋",
  "textTranslated": "N/A",
  "language": "en",
  "publishedAt": "2026-09-24T16:31:57.737Z",
  "publishedAtRelative": "3 hours ago",
  "likesCount": 0,
  "reactionsCount": 0,
  "ownerResponseText": "N/A",
  "ownerResponseRelative": "N/A",
  "reviewerName": "Mary Downs",
  "reviewerId": "116325683602922945114",
  "reviewerUrl": "https://www.google.com/maps/contrib/116325683602922945114/reviews",
  "reviewerReviewsCount": 28,
  "reviewerPhotosCount": 21,
  "isLocalGuide": "Yes",
  "placeName": "Giordano's",
  "placeId": "ChIJh3i0BqYsDogR6yp0y6TFlOQ",
  "placeFid": "0x880e2ca606b47887:0xe494c5a4cb742aeb",
  "placeCid": "16471007048779442923",
  "placeAddress": "130 E Randolph St, Chicago, IL 60601",
  "placeCategory": "Pizza restaurant",
  "placeRating": 4.5,
  "placeTotalReviews": 26763,
  "placeUrl": "https://www.google.com/maps/place/?q=place_id:ChIJh3i0BqYsDogR6yp0y6TFlOQ",
  "placeLatitude": 41.8851301,
  "placeLongitude": -87.62376119999999,
  "placeWebsite": "https://giordanos.com/locations/prudential-plaza-millennium-park/",
  "placePhone": "+13126161200",
  "sortOrder": "newest",
  "inputQuery": "pizza in Chicago, IL",
  "reviewContext": { "Meal type": "Dinner" },
  "subRatings": { "Food": 5, "Service": 5, "Atmosphere": 5 },
  "reviewImageUrls": [],
  "placeCategories": ["Pizza restaurant", "Delivery service", "Takeout Restaurant", "Pizza delivery"],
  "scrapedAt": "2026-09-24T19:34:12.047Z",
  "error": null
}
```

A review written in another language keeps the original and adds the translation, from the same run:

```json
{ "text": "ساندوش ستيك لحم كان جميل ولذيذ", "textTranslated": "The steak sandwich was beautiful and delicious.", "language": "ar" }
```

A field the review does not have reads `"N/A"` (no text on a star-only review, no owner reply), and empty lists are `[]`. A row with `error` set is an input that could not be read; it is never billed.

### Configure the run

Mix place URLs, place IDs and searches in one run. The Input tab lists every option.

New reviews from the last day for two locations, newest first:

```json
{ "startUrls": [{ "url": "https://www.google.com/maps/place/Katz%27s+Delicatessen/data=!4m2!3m1!1s0x89c2598f7ff4aa09:0x313547e757cb8cea" }], "placeIds": ["ChIJh3i0BqYsDogR6yp0y6TFlOQ"], "sort": "newest", "reviewsNewerThan": "1 day" }
```

The 1 and 2 star reviews with text for the top 10 dentists in a city:

```json
{ "searchTerms": ["dentist"], "location": "Austin, TX", "maxPlacesPerSearch": 10, "sort": "lowestRating", "starRatings": ["1", "2"], "onlyWithText": true }
```

### Pricing

Pay-per-event: **$0.60 per 1,000 reviews**, dropping to $0.534 per 1,000 on higher Apify plans, plus a run-start fee of $0.005. You pay only for reviews written to your dataset; error rows are free.

| Reviews collected | Approximate cost |
|---|---|
| 100 | $0.07 |
| 1,000 | $0.61 |
| 10,000 | $6.01 |

New Apify accounts start with $5 in free credit.

### Free users

Free-plan runs return up to 10 reviews as a preview. [Upgrade your Apify plan](https://console.apify.com/sign-up?fpr=vmoqkp) to collect up to 1,000,000 reviews per run.

### Run it

1. [Create a free Apify account with $5 in credit](https://console.apify.com/sign-up?fpr=vmoqkp).
2. Open the Google Maps Reviews Scraper.
3. Paste place URLs or place IDs, or enter a search term and a location, pick a sort order and any filters, and click **Start**.
4. Export the reviews as CSV, Excel, JSON, or XML from the **Dataset** tab, or schedule the run for ongoing review monitoring.

Run it programmatically through the [Apify API](https://docs.apify.com/api/v2?fpr=vmoqkp) or the [ApifyClient](https://docs.apify.com/api/client/js?fpr=vmoqkp) for JavaScript and Python.

### Use with AI agents (MCP)

Give an AI agent live Google reviews through the Model Context Protocol. Add the Actor to Claude, Cursor, or any MCP client:

```bash
claude mcp add --transport http apify "https://mcp.apify.com?tools=parseforge/google-maps-reviews-scraper"
```

Then prompt it in plain language:

- *"Get this week's Google reviews for our three locations and list every review under 3 stars that has no owner reply."*
- *"Compare the Food, Service and Atmosphere scores of the top 10 pizza places in Chicago."*
- *"Summarize what customers say about wait times at this restaurant, in Spanish."*

Copy this into ChatGPT, Claude, or Cursor to start:

```
Use the Apify Actor "parseforge/google-maps-reviews-scraper" to collect Google Maps reviews. Input: { "startUrls": [{ "url": "<google maps place url>" }], "placeIds": ["<ChIJ...>"], "searchTerms": ["<what>"], "location": "<where>", "sort": "<newest|mostRelevant|highestRating|lowestRating>", "reviewsNewerThan": "<30 days>", "maxItems": <n> }. Reviews come back with rating, text, textTranslated, publishedAt, likesCount, ownerResponseText, reviewerName, placeName, placeRating and placeTotalReviews. Call it with the ApifyClient and my APIFY_TOKEN.
```

### Troubleshooting

**Why am I getting no results?**

The URL may not point at a single place, or the place ID may be wrong; the run writes an `error` row that says so. A filter can also remove everything: loosen `starRatings`, `reviewTextContains` or `reviewsNewerThan`.

**Why fewer reviews than the place total?**

Google's review list for signed-out visitors is shorter than the lifetime total, and your filters remove more. Compare your count with `placeTotalReviews` on any row.

**Why did the sort change to newest?**

"Only reviews newer than" needs newest-first order to know where to stop, so the run switches to it and says so in the log.

**Why does "Most relevant" differ between languages?**

Google ranks relevance per language, so the same place returns a different first page in English and in Spanish.

**Can I search inside the review text?**

Yes, with `reviewTextContains`. Google offers no review search to signed-out visitors, so the Actor reads the reviews and keeps the matching ones; you pay only for the matches.

### FAQ

| Question | Answer |
|---|---|
| Do I need a Google API key or account? | No. It reads Google Maps' public review list, with no login, cookies or key. |
| How is this different from the Google Places API? | The Places API returns at most 5 reviews per place. This returns the full list Google Maps shows, sorted and filtered your way. |
| Are the dates exact? | Yes. `publishedAt` is Google's own timestamp of the review (or of its last edit), in ISO 8601. |
| Does it include owner replies? | Yes, `ownerResponseText` and `ownerResponseRelative` on every review that has one. |
| Can it translate reviews? | Google does: pick `language`, and reviews in other languages come with `textTranslated`. |
| Can I filter by stars or date? | Yes: `starRatings`, `reviewsNewerThan`, `reviewTextContains`, `onlyWithText` and `onlyWithOwnerResponse`. |
| Which inputs work? | Place URLs, maps.app.goo.gl share links, ?cid= links, Maps search URLs, ChIJ place IDs, feature IDs, CIDs, and a search term with a location. |
| How many places does a search return? | Up to `maxPlacesPerSearch`. Google stops a single Maps search after a couple of hundred places at most (108 for "restaurants in Chicago, IL" in our test), so split big areas into neighborhoods. |
| How many reviews per run? | Free plan: 10. Paid: up to 1,000,000, bounded by what Google lists for each place and your filters. |
| Do I need a proxy? | Usually not. The run connects directly and switches to Apify Proxy by itself if Google starts refusing. |
| Is this an official Google product? | No. It is unofficial and reads only public Google Maps data. |

### Related actors

- [Google Maps Contacts Scraper](https://apify.com/parseforge/google-maps-contacts-scraper?fpr=vmoqkp): businesses from Google Maps with the email and phone from their own website.
- [Google Maps Shared List Scraper](https://apify.com/parseforge/google-maps-shared-list-scraper?fpr=vmoqkp): every place in a shared Google Maps list.
- [TikTok Comments Scraper](https://apify.com/parseforge/tiktok-comments-scraper?fpr=vmoqkp): public comments on TikTok videos.
- [YouTube Transcript Scraper](https://apify.com/parseforge/youtube-transcript-scraper?fpr=vmoqkp): transcripts from YouTube videos.
- [Kayak Scraper](https://apify.com/parseforge/kayak-scraper?fpr=vmoqkp): flight and hotel prices from Kayak.

Browse the full [ParseForge collection](https://apify.com/parseforge?fpr=vmoqkp) for more scrapers.

🆘 **Need help?** [Open our contact form](https://tally.so/r/BzdKgA) with your run ID, your input, and what you expected.

⚠️ **Disclaimer.** This Actor is unofficial and is not affiliated with, endorsed by, or sponsored by Google LLC. It collects only publicly available Google Maps data. You are responsible for using the data in compliance with Google's terms and applicable laws, including GDPR and CCPA. Do not use it to identify, profile, or target individuals.

# Actor input Schema

## `startUrls` (type: `array`):

Place links copied from Google Maps (the long /maps/place/... URL, a maps.app.goo.gl share link, a ?cid= link, or a /maps/search/... link).

## `placeIds` (type: `array`):

Google place IDs (ChIJ...), feature IDs (0x...:0x...) or CID numbers, one per line.

## `searchTerms` (type: `array`):

Find places by what they are, like "pizza" or "dentist". Each term returns up to "Max places per search" places, and their reviews.

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

Where to search, like "Austin, TX" or "Madrid, Spain". Added to every search term.

## `maxItems` (type: `integer`):

Free users: Limited to 10 items (preview). Paid users: Optional, max 1,000,000

## `maxReviewsPerPlace` (type: `integer`):

Stop each place after this many reviews. Leave empty for every review Google shows.

## `maxPlacesPerSearch` (type: `integer`):

How many places each search term (or /maps/search/ URL) contributes. Google returns about 20 places per page.

## `sort` (type: `string`):

Google's review order. "Only reviews newer than" always uses newest first.

## `reviewsNewerThan` (type: `string`):

A date (2026-01-31) or a window ("30 days", "6 months", "1 year"). The run stops reading a place once it reaches older reviews.

## `starRatings` (type: `array`):

Keep only reviews with these ratings. Leave empty for all. With highest or lowest sort the run stops a place as soon as the ratings run out of range.

## `reviewTextContains` (type: `array`):

Keep only reviews whose text (or its translation) contains at least one of these words. Google has no review search for signed-out visitors, so the Actor reads the reviews and filters them itself.

## `onlyWithText` (type: `boolean`):

Skip star-only reviews.

## `onlyWithOwnerResponse` (type: `boolean`):

Keep only reviews that carry a response from the business.

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

Reviews written in another language come with Google's translation into this one in textTranslated. The original text is always kept.

## `concurrency` (type: `integer`):

How many places are read at the same time.

## `proxyConfiguration` (type: `object`):

Off by default: Google answers these requests directly. If Google starts refusing, the run switches to Apify Proxy on its own.

## Actor input object example

```json
{
  "startUrls": [
    {
      "url": "https://www.google.com/maps/place/Katz%27s+Delicatessen/data=!4m2!3m1!1s0x89c2598f7ff4aa09:0x313547e757cb8cea"
    }
  ],
  "maxItems": 10,
  "maxPlacesPerSearch": 5,
  "sort": "newest",
  "onlyWithText": false,
  "onlyWithOwnerResponse": false,
  "language": "en",
  "concurrency": 3,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}
```

# Actor output Schema

## `overview` (type: `string`):

Key review fields

## `fullData` (type: `string`):

Complete dataset with all 40 fields

# 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 = {
    "startUrls": [
        {
            "url": "https://www.google.com/maps/place/Katz%27s+Delicatessen/data=!4m2!3m1!1s0x89c2598f7ff4aa09:0x313547e757cb8cea"
        }
    ],
    "maxItems": 10,
    "proxyConfiguration": {
        "useApifyProxy": false
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("parseforge/google-maps-reviews-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 = {
    "startUrls": [{ "url": "https://www.google.com/maps/place/Katz%27s+Delicatessen/data=!4m2!3m1!1s0x89c2598f7ff4aa09:0x313547e757cb8cea" }],
    "maxItems": 10,
    "proxyConfiguration": { "useApifyProxy": False },
}

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

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

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

```

## CLI example

```bash
echo '{
  "startUrls": [
    {
      "url": "https://www.google.com/maps/place/Katz%27s+Delicatessen/data=!4m2!3m1!1s0x89c2598f7ff4aa09:0x313547e757cb8cea"
    }
  ],
  "maxItems": 10,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}' |
apify call parseforge/google-maps-reviews-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,parseforge/google-maps-reviews-scraper"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

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