Skip to content

domain-skill: google-maps reviews scraping#489

Open
theoutsider04 wants to merge 1 commit into
browser-use:mainfrom
theoutsider04:google-maps-reviews
Open

domain-skill: google-maps reviews scraping#489
theoutsider04 wants to merge 1 commit into
browser-use:mainfrom
theoutsider04:google-maps-reviews

Conversation

@theoutsider04

@theoutsider04 theoutsider04 commented Jul 6, 2026

Copy link
Copy Markdown

Adds domain-skills/google-maps/reviews.md — field-tested flow for scraping all reviews of a business profile: place_id / CID URL patterns, hl= language trick to get original vs auto-translated texts, feed-container scrolling, stable selectors, and the rating-only-review trap where the owner's reply leaks as the review text.

🤖 Generated with Claude Code


Summary by cubic

Add a field-tested guide for scraping all reviews from a Google Maps business profile without an API key. It shows URL patterns (search, place_id, CID, deep links), a stable reviews-tab + feed-container scroll + expand flow, how to use hl= to capture originals vs translations, and traps like rating-only reviews leaking owner replies.

Written for commit 823c3f4. Summary will update on new commits.

Review in cubic

@browser-harness-review

Copy link
Copy Markdown

✅ Skill review passed

Reviewed 1 file(s) — no findings.

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

2 issues found across 1 file

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="domain-skills/google-maps/reviews.md">

<violation number="1" location="domain-skills/google-maps/reviews.md:9">
P2: The guidance overstates the reliability of the two-language `hl` heuristic. It claims that scraping in two UI languages always yields one original and one translation per review, but this only holds when a review's original language matches one of the two `hl` values. For reviews in a third language, both scrapes produce translations — so downstream consumers may mislabel translated text as "original." Consider qualifying this (e.g., "one scrape may match the reviewer's language, yielding the original, while the other is translated") or noting that the approach only works when the review language is known to match one of your chosen `hl` values. If you can access per-review language metadata (analogous to the Places API's `textLanguageCode`), that would be a more reliable signal.</violation>

<violation number="2" location="domain-skills/google-maps/reviews.md:21">
P2: The extraction example doesn't implement the deduping guard that its own documentation recommends. The 'Traps' section says duplicate `div[data-review-id]` nodes are removed by '[jsaction] filter **plus** name-presence check,' but the code block only applies the `[jsaction]` selector and never checks that `name` is truthy before processing the element. If a user copies this example, duplicate card/expanded-state nodes will be emitted as separate reviews. Consider adding a `if (!name) return;` guard (or a `data-review-id` Set) so the sample matches the described deduping logic.</violation>
</file>

Reply with feedback, questions, or to request a fix.

Fix all with cubic | Re-trigger cubic


- Search: `https://www.google.com/maps/search/<business>+<city>` — a unique match redirects straight to the place page.
- Direct by place_id: `https://www.google.com/maps/place/?q=place_id:<PLACE_ID>` — resolves and redirects to the canonical place URL.
- **Language matters:** Google auto-translates reviews into the UI language. Add `hl=fr` (etc.) and re-scrape to get originals — for each review, one language is the reviewer's original and the other is Google's translation. Scrape both if you need the pair.

@cubic-dev-ai cubic-dev-ai Bot Jul 6, 2026

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: The guidance overstates the reliability of the two-language hl heuristic. It claims that scraping in two UI languages always yields one original and one translation per review, but this only holds when a review's original language matches one of the two hl values. For reviews in a third language, both scrapes produce translations — so downstream consumers may mislabel translated text as "original." Consider qualifying this (e.g., "one scrape may match the reviewer's language, yielding the original, while the other is translated") or noting that the approach only works when the review language is known to match one of your chosen hl values. If you can access per-review language metadata (analogous to the Places API's textLanguageCode), that would be a more reliable signal.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At domain-skills/google-maps/reviews.md, line 9:

<comment>The guidance overstates the reliability of the two-language `hl` heuristic. It claims that scraping in two UI languages always yields one original and one translation per review, but this only holds when a review's original language matches one of the two `hl` values. For reviews in a third language, both scrapes produce translations — so downstream consumers may mislabel translated text as "original." Consider qualifying this (e.g., "one scrape may match the reviewer's language, yielding the original, while the other is translated") or noting that the approach only works when the review language is known to match one of your chosen `hl` values. If you can access per-review language metadata (analogous to the Places API's `textLanguageCode`), that would be a more reliable signal.</comment>

<file context>
@@ -0,0 +1,36 @@
+
+- Search: `https://www.google.com/maps/search/<business>+<city>` — a unique match redirects straight to the place page.
+- Direct by place_id: `https://www.google.com/maps/place/?q=place_id:<PLACE_ID>` — resolves and redirects to the canonical place URL.
+- **Language matters:** Google auto-translates reviews into the UI language. Add `hl=fr` (etc.) and re-scrape to get originals — for each review, one language is the reviewer's original and the other is Google's translation. Scrape both if you need the pair.
+- The place URL contains the ftid `!1s0x...:0x<hex>` — the hex after the colon is the CID: `int(hex, 16)` → `https://maps.google.com/?cid=<decimal>`.
+- All-reviews / write-review deep links (no Maps UI): `https://search.google.com/local/reviews?placeid=<PLACE_ID>` and `https://search.google.com/local/writereview?placeid=<PLACE_ID>`.
</file context>
Suggested change
- **Language matters:** Google auto-translates reviews into the UI language. Add `hl=fr` (etc.) and re-scrape to get originals — for each review, one language is the reviewer's original and the other is Google's translation. Scrape both if you need the pair.
- **Language matters:** Google auto-translates reviews into the UI language. Add `hl=fr` (etc.) and re-scrape — if the reviewer's original language matches this `hl`, you'll get the original text; otherwise you'll get a Google translation. For reviews in languages other than your chosen `hl` values, both scrapes may be translations, so this heuristic only reliably yields an original/translation pair when the review language is known to match one of your `hl` settings. Scrape both if you need the pair.
Fix with cubic

4. Extract per card:

```js
document.querySelectorAll('div[data-review-id][jsaction]').forEach(el => {

@cubic-dev-ai cubic-dev-ai Bot Jul 6, 2026

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: The extraction example doesn't implement the deduping guard that its own documentation recommends. The 'Traps' section says duplicate div[data-review-id] nodes are removed by '[jsaction] filter plus name-presence check,' but the code block only applies the [jsaction] selector and never checks that name is truthy before processing the element. If a user copies this example, duplicate card/expanded-state nodes will be emitted as separate reviews. Consider adding a if (!name) return; guard (or a data-review-id Set) so the sample matches the described deduping logic.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At domain-skills/google-maps/reviews.md, line 21:

<comment>The extraction example doesn't implement the deduping guard that its own documentation recommends. The 'Traps' section says duplicate `div[data-review-id]` nodes are removed by '[jsaction] filter **plus** name-presence check,' but the code block only applies the `[jsaction]` selector and never checks that `name` is truthy before processing the element. If a user copies this example, duplicate card/expanded-state nodes will be emitted as separate reviews. Consider adding a `if (!name) return;` guard (or a `data-review-id` Set) so the sample matches the described deduping logic.</comment>

<file context>
@@ -0,0 +1,36 @@
+4. Extract per card:
+
+```js
+document.querySelectorAll('div[data-review-id][jsaction]').forEach(el => {
+  const name  = el.querySelector('.d4r55')?.textContent?.trim();   // reviewer name
+  const stars = el.querySelector('.kvMYJc')?.getAttribute('aria-label'); // "5 stars"/"5 étoiles"
</file context>
Fix with cubic

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant