Try it
Run a live Google Maps request
One real call, no signup and no key. Search any city and get ranked places with phone, website, hours and rating.
What you get
What a Place Record Actually Contains
The cheap end of this market returns a name, an address and a rating. This is the whole record, field by field, as it arrives.
Identity & rank
- rank
- place_id
- data_id
- maps_url
- name
- description
- categories[]
- business_status
- detail_status
Contact & location
- address.formatted
- address.street, address.city
- address.postal_code, address.state
- address.country, address.borough
- coordinates.latitude
- coordinates.longitude
- phone
- website
- timezone, plus_code
Reputation
- rating
- review_count
- review_distribution.1…5
- price_range
- opening_hours
Visit planning
- popular_times
- amenities[].options[]
- service_options[].options[]
- links.booking[]
- links.menu
- links.order_online[]
Media & ownership
- cover_image
- image_count
- images[].url, images[].label
- ownership.claimed
- ownership.owner_name
- ownership.owner_id
Review records
- review_id, review_url
- rating
- text.original, text.translated
- published_at, updated_at
- relative_date, images[]
- detailed_ratings
- owner_response.*
- reviewer.name, reviewer.local_guide
A name and a pin is where this record starts, not where it ends. Every place carries its identifiers (place_id, data_id and a public maps_url), a seven-part address — borough, street, city, postal code, state, country and the formatted line — plus coordinates, phone, website, rating, review count, business status, price range, timezone and plus_code. A fully-enriched record adds opening_hours, popular_times, amenities, service_options, the 1–5 review_distribution, the booking, menu and order-online links, the labelled images array with cover_image and image_count, and ownership — whether the listing is claimed, and by whom.
The extra fields are the product. An unclaimed listing with 40 reviews and no website is a different prospect from a claimed one with a booking link and a Friday-evening rush in popular_times. That is the difference between a directory row and a qualified lead, and it is the part of the record the cheap end of this market does not return. A row that costs a hundredth as much and answers a tenth of your questions is not the same product.
A missing detail is not a missing place. Search preserves the ranked core record when a full detail read does not finish inside the request window, so you get the row rather than a hole. Every response says so in numbers: counts carries requested, discovered, returned, fully_enriched and core_only; meta.partial is the boolean; and when fewer places were opened than you asked for, a top-level delivery block adds requested, returned, a reason, a one-line note and an async_endpoint pointer at the job form. Reviews carries the same block against its page size of 20. Measured 2026-08-06: a bounded deep call discovered and returned 97 of the 100 places it requested.
How you pay
No Monthly Plan, No Minimum, Nothing Renews
Growth and Scale are one-time deposits. There is no subscription holding your rate, and no volume floor you have to keep re-hitting to keep it.
One deposit, kept for good
Growth unlocks on a one-time $100 deposit and Scale on $500. The tier is locked once earned, so it never downgrades when the balance falls, and nothing renews.
There is no subscription, no monthly commitment and no minimum payment. You pay per call at the tier you unlocked, and you stop paying the moment you stop calling.
Every rate that beats ours has a floor
Five vendors publish a lower price per place than we do and one publishes a lower price per review. Every one of those rates needs either a recurring monthly plan or a minimum payment before it exists at all.
Outscraper’s cheap tier is volume-banded inside a rolling 30 days, so it holds only if you re-hit 100,000 records every month. The exact figures are in the tables below.
Google’s free tier returns IDs, not businesses
Google Places Text Search has a free Essentials band, and it is genuinely free at unlimited volume — but what it returns is place IDs. The first Google tier that hands back a business name and address is Text Search Pro at $32.00 per 1,000 requests, up to 20 places a request.
Place Details Essentials starts at $5.00 per 1,000 requests and Place Details Pro at $17.00. Google’s own volume discounts do not begin until you are past five million calls a month. Google pricing checked 2026-09-08.
free calls, then per call
New accounts get Free to start, shared across every endpoint, and all four Maps endpoints can spend them.
Billing is per call, not per record: a quick search that returns twenty places is one charge. Valid empty results and successful partial results are billable calls.
Endpoints & Pricing
Four Maps Endpoints, One API Key
Pick the smallest call that does the job. Each endpoint has its own published rate, and Maps carries its own 10% Growth and 30% Scale discounts.
Quick Search
GET /api/maps/search/quick- Up to 20 ranked places, all fully enriched
- Query only, or
locationtext, or alat/lngpair startoffset of 0, 20, 40, 60 or 80
Deep Search
GET /api/maps/search- The whole discovered list, up to 100 places
detailsets how many of those get a full record- Premium band above
detail=20— see the note below
Place Details
GET /api/maps/place- One business record at the richest available detail
- Keyed by
place_id,data_idor a Google Maps URL - The cheapest way to refresh a known listing
Reviews
GET /api/maps/reviews- Up to 20 reviews a call — page size is request size
- Reviewer fields, owner response, detailed ratings
sort: relevant, newest, highest, lowest
Deep has two flat bands, and the step between them is a cliff. You always get the whole ranked list of up to 100 places; detail only sets how many of those records are fully enriched, and the rest come back as core_only entries that still carry name, address, coordinates, rating, review count, phone and website. detail 0–20 costs $0.0150 a call; detail 21–100 costs a flat $0.0750 a call, so 21 and 99 are the same price. detail=20 bills $0.0150 and detail=21 bills $0.0750 — 5× for one extra fully-enriched place. The default on GET /api/maps/search is detail=20, inside the cheap band.
Now the unit that matters. At detail=20 that is $0.15 per 1,000 places returned and $0.75 per 1,000 fully-enriched places. At detail=100 it is $0.75 per 1,000 places returned and $0.75 per 1,000 fully-enriched places — the same fully-enriched rate at both ends of the product. Between them the premium band is worse per record ($2.50 per 1,000 fully-enriched places at detail=30), so buy at 20 or at 100 unless a specific depth is what you need. Quick is $0.0150 a call and fully enriches every place it returns, up to 20, also $0.75 per 1,000 fully-enriched places: Deep at its default costs the same and adds up to 80 more core_only places on top, while Quick stays the faster response and the one with start paging. Synchronous Deep is capped at detail=30 for latency, not price — 21–30 works synchronously at the premium rate, and higher depths are submitted as a job. Read limits.endpoints[…].async_available from GET /api/status to confirm the job surface is available on your account.
Quick Start
Ranked Places in One Request
One header, one query string. The path is the only thing that changes between a place search, a single business record and a page of reviews.
# Up to 20 ranked places, every one of them fully enriched curl -G "https://apiserpent.com/api/maps/search/quick" \ --data-urlencode "q=coffee" \ --data-urlencode "location=Brooklyn, NY" \ -d "country=us" \ -H "X-API-Key: YOUR_API_KEY" # The whole discovered list, up to 100 places. detail=20 is the default and the cheap band. curl -G "https://apiserpent.com/api/maps/search" \ --data-urlencode "q=dentist" \ --data-urlencode "location=Manchester" \ -d "detail=20" \ -H "X-API-Key: YOUR_API_KEY" # One business record, and then its reviews, newest first curl "https://apiserpent.com/api/maps/place?place_id=PLACE_ID" \ -H "X-API-Key: YOUR_API_KEY" curl "https://apiserpent.com/api/maps/reviews?place_id=PLACE_ID&sort=newest" \ -H "X-API-Key: YOUR_API_KEY"
# Quick search pages 20 at a time through the start offsets 0, 20, 40, 60, 80. import csv, requests BASE = "https://apiserpent.com/api/maps/search/quick" HEAD = {"X-API-Key": "YOUR_API_KEY"} rows = [] for start in (0, 20, 40, 60, 80): r = requests.get(BASE, headers=HEAD, params={ "q": "plumber", "location": "Austin, TX", "country": "us", "start": start, }, timeout=60) data = r.json() for p in data.get("places", []): rows.append([p["name"], p["phone"], p["website"], p["rating"], p["review_count"], p["address"]["formatted"], p["detail_status"]]) # detail_status is "complete" or "core_only" — never guess which fields are trustworthy. with open("places.csv", "w", newline="") as f: csv.writer(f).writerows(rows)
// Follow the token the response hands you. Never manufacture an offset — // review order changes over time and an invented offset silently skips rows. const KEY = process.env.SERPENT_KEY; let token = null, all = []; do { const qs = new URLSearchParams({ place_id: 'PLACE_ID', sort: 'newest' }); if (token) qs.set('page_token', token); const res = await fetch(`https://apiserpent.com/api/maps/reviews?${qs}`, { headers: { 'X-API-Key': KEY } }); const body = await res.json(); all.push(...body.reviews); token = body.next_page_token ?? null; // absent on the last page } while (token); console.log(`${all.length} reviews, up to 20 per call`);
{
"success": true,
"query": "coffee",
"type": "maps",
"endpoint": "quick",
"places": [
{
"rank": 1,
"place_id": "ChIJExample000000000000000",
"name": "Example Coffee",
"categories": ["Coffee shop", "Espresso bar"],
"address": { "formatted": "12 Example St, Brooklyn, NY 11201" },
"coordinates": { "latitude": 40.6988, "longitude": -73.9903 },
"phone": "+1 718-555-0123",
"website": "https://example.com",
"rating": 4.6,
"review_count": 1284,
"review_distribution": { "5": 912, "4": 241, "3": 78, "2": 28, "1": 25 },
"price_range": "$$",
"business_status": "OPERATIONAL",
"ownership": { "claimed": true, "owner_name": "Example Coffee" },
"detail_status": "complete"
}
],
"counts": {
"requested": 20,
"discovered": 20,
"returned": 20,
"fully_enriched": 19,
"core_only": 1
},
"delivery": {
"requested": 20,
"returned": 19,
"reason": "deadline_reached",
"note": "Delivered the results gathered within this request.",
"async_endpoint": "/api/bulk/jobs"
},
"meta": { "partial": true }
}
Read detail_status before you read a record. It is complete, core_only or null, and a nullable field on a core_only record means unknown, not absent — a classifier that reads a blank website as “this business has no site” will be wrong on every partial row.
Why Maps business data
What Google Maps business data is, and why teams use it
Maps is where local businesses are described, ranked and reviewed in public. Four things follow from that, and they are why teams pay for the data.
Often the only structured record
A place record is the closest thing to a public profile most local businesses have: who they are, where they are, when they are open, what they sell and what customers said about it.
For a great many of them there is no website, no filing and no directory entry to fall back on. The listing is the record, which is why its completeness decides what you can actually do with it.
One shape across four endpoints
Quick search, deep search and place details all answer in the same normalized place shape, so a consumer can depend on field names and read detail_status instead of branching per endpoint.
Reviews returns that same place block alongside its page of reviews, so a change feed never has to look the business up again to know what it belongs to.
Claimed, unclaimed, closed
ownership.claimed and ownership.owner_name say whether a business is watching its own listing. business_status says whether it is open, temporarily closed or permanently closed.
Together they are the difference between a lead list and a list of addresses. A permanently-closed listing still appears in results; it just is not a customer.
What this is not
This is a data API, not a map SDK. It does not render maps and it does not provide directions, route optimization, navigation, geocoding or autocomplete widgets. If you need a map on a screen, you need Google’s SDK, not this.
Search can also return fewer places than the maximum you asked for, and fields vary by listing — treat a null on a core_only row as unknown rather than as a confirmed absence.
Price comparison
Where We Sit on Price, Including Where We Lose
Five vendors publish a lower price per place than we do and one publishes a lower price per review. Every one of them is named below.
| Provider | Unit charged | Cost per 1,000 | What the lowest rate requires | Free tier |
|---|---|---|---|---|
| DataForSEO Maps SERP | per SERP page, up to 100 results | $0.006/1K places | $50 minimum payment; Standard queue | None published |
| ScrapingDog Maps | per request, ~20 places | $0.00675/1K places | $30,000/month plan | 200 credits |
| HasData Maps Search | per request, ~20 places | $0.0175/1K places | $208/month recurring plan | 200 searches/month |
| SerpApi Maps | per search, 20 per page | $0.098/1K places | $106,050/month plan | 250 searches/month |
| Google Places Text Search Pro | per request, up to 20 places | $0.12/1K places | Over 5,000,000 calls a month | 5,000 requests/month |
| Serpent (ours) | per call — up to 20 Quick, up to 100 Deep | $0.525/1K places | One $500 deposit, once. No monthly plan. | Free to start |
| Outscraper Maps | per place | $1.00/1K places | 100,000+ records inside a rolling 30 days — the tier resets | First 500 free |
Apify compass/crawler-google-places |
per place | from $1.50/1K places | Apify Scale $199/month or Business $999/month | $5 credit/month |
| Provider | Unit charged | Cost per 1,000 | What the lowest rate requires | Free tier |
|---|---|---|---|---|
| DataForSEO Google Reviews | per 10 reviews | $0.075/1K reviews | $50 minimum payment; Standard queue | None published |
| Serpent (ours) | per call — up to 20 reviews | as little as $0.105/1K reviews | One $500 deposit, once. No monthly plan. | Free to start |
| Apify review add-on | per review | $0.50/1K reviews | Sold as an add-on to the places actor | $5 credit/month |
| Outscraper Reviews | per review | $1.00/1K reviews | 100,000+ records inside a rolling 30 days | First 500 free |
Our figures are the Scale rate, so every competitor column shows that vendor’s lowest published rate too — not their entry rate. Places: a quick call returns up to 20 fully-enriched places for $10.50 per 1,000 calls, which is $0.525 per 1,000 places; a deep call at detail=100 prices a fully-enriched place identically. Reviews: a call returns up to 20 reviews for $2.10 per 1,000 calls, so as little as $0.105 per 1,000 reviews when a full page returns — 20 is the page size, not a guarantee, and a short page costs the same call. Competitor rates were read from each vendor’s own pricing page on 2026-09-08; where a vendor publishes no free tier we say so rather than guess.
Read the fourth column before the third. Four of the rates above need a recurring plan or a minimum payment to exist at all — $30,000 a month, $208 a month, $106,050 a month, or a $50 minimum top-up. Outscraper’s cheap tier is volume-banded inside a rolling 30 days, so it holds only if you re-hit 100,000 records every month. Our Growth and Scale tiers are single one-time deposits of $100 and $500, they are locked once earned, and they never downgrade if your balance falls. Nothing renews and there is no minimum spend.
And compare the record, not only the rate. The field list at the top of this page is what our rate buys: popular times, amenities, service options, the labelled photo array, the 1–5 review distribution and whether a listing is claimed, and by whom. Those are fields the cheap end of this table does not return.
Use cases
What Teams Actually Pull Maps Data For
Four jobs that account for most Maps traffic, and the endpoint and parameters each one needs.
Local lead lists
Quick search across a city’s start offsets gives you name, phone, website, rating and review count at 20 places a call. Filter on a blank website and you have a list of businesses to build sites for.
Only classify rows whose detail_status is complete. A blank field on a core_only row means the record was not finished, not that the business has no site.
Local pack rank tracking
Deep search preserves discovered rank order across the whole list, so you can log where a client sits for “plumber near me” week over week and see who moved above them.
zoom and a lat/lng pair pin the search to the point you care about, which is what makes two weeks’ results comparable. See local rank tracking.
Review monitoring
One reviews call returns up to 20 reviews with the review text, its language variants, detailed ratings, the reviewer and any owner response. sort=newest plus the page token is a complete change feed.
Store the review_id and stop paging when you reach one you have already seen — that turns a full backfill into a cheap daily delta.
Competitor and category audits
Pull the same query in twenty cities and you have a category map: who is claimed, who has a booking link, what the price bands look like, and how the review distribution differs by market.
Place details is the cheapest refresh path at $1.05 per 1,000 calls on Scale — keep the place_id and re-read the record instead of re-running the search.
FAQ
Google Maps API Questions
counts (requested, discovered, returned, fully_enriched, core_only) and sets meta.partial to true. Alongside those, a top-level delivery block reports the enrichment as requested and returned with a reason, a one-line note and an async_endpoint pointer at the job form. Reviews carries the same block against its page size of 20.
https://api.apiserpent.com/api/maps/*. Verify them live in the playground with your API key before production integration, and check the account's free-call and credit status first.
q is required. Location is set either by location as free text or by a lat and lng pair, which can also be written as the ll alias in lat,lng form. They are mutually exclusive: sending two of them is a 400 rather than a silent choice between two places you named. country is a two-letter code and defaults to us, language is a two-letter code and defaults to en, and zoom runs 1 to 21 and defaults to 14. Quick search additionally takes start; deep search takes detail. Reviews and place details take exactly one of place_id, data_id or a Google Maps URL, and reviews adds sort with relevant, newest, highest or lowest.
Start using the Google Maps API
free API calls, shared across every endpoint. No card, no subscription, no minimum spend, and nothing renews.
Try for Free

