# Changelog of SiteVerdict — Local Business Leads (Google Places API + OSM) (`siteverdict/siteverdict-local-business-leads`) Actor

- **URL**: https://apify.com/siteverdict/siteverdict-local-business-leads/changelog.md
- **Full Actor documentation**: https://apify.com/siteverdict/siteverdict-local-business-leads.md

## Changelog

### Unreleased (prepared 2026-10-15, NOT pushed) — Private-network (SSRF) protection

- Custom `overpassUrl` / `nominatimUrl` must be public http(s) hosts. Private, loopback, link-local, cloud-metadata and internal addresses (in every IP encoding, and names that resolve to such addresses) are refused before any request is made; the run stops with "Refused: … private-network protection; not charged".
- Both OSM clients use a DNS-pinned transport that re-checks every redirect hop (shared SiteVerdict guard, `src/ssrf-guard.ts` + `src/netguard.ts`).
- No change to output fields or pricing.

### Memory default (15 Oct 2026)

- 15 Oct 2026 (build after this entry): default run memory is now 512 MB via `defaultMemoryMbytes` (the old defaultRunOptions 512 MB was ignored so runs used 4096 MB; peak 72-84 MB). Measured on the example input: same output, see the public-15 remediation log. You can still choose more memory per run. No change to inputs, outputs or pricing.

### 1.0.0 (11 Oct 2026)

First release.

#### Sources

- **OpenStreetMap:**
  - Overpass API queries built from about 60 plain-English categories, mapped to OSM tags.
  - Name-match fallback for unknown categories, or custom tags you supply.
  - Nominatim geocoding.
  - Polite clients: identifying User-Agent, 1.1 s Nominatim pacing, one Overpass request at a time with pauses, backoff on 429/504 and Retry-After.
  - Custom Overpass and Nominatim endpoints.
- **Google Places API (New)** with the user's own key (secret input):
  - Text Search (New), Nearby Search (New) and Place Details (New).
  - Field-mask presets: IDs only, Basic, Contact and Atmosphere.

#### Grid search

- Areas: point + radius, bounding box, GeoJSON polygon, or a geocoded place.
- The area is tiled. Tiles that saturate the cap (60 for Text Search, 20 for Nearby) are split into 4, up to a depth and tile cap.
- De-duplication by place ID / OSM id.

#### Cost controls

- Pre-run Google cost estimate (expected, worst case, ceiling) using Google list prices checked 11 Oct 2026.
- Price overrides.
- A list-price budget cap that stops the run cleanly.
- Dry-run mode.

#### Robustness

- Error handling for:
  - `PERMISSION_DENIED`, `API_KEY_INVALID`, `REQUEST_DENIED`: stop the Google path with a clear message.
  - `RESOURCE_EXHAUSTED`, `OVER_QUERY_LIMIT`, 5xx: exponential backoff with jitter.
  - Invalid requests: skip and continue.
- The API key is redacted from all logs and errors.

#### Output

- Normalised business records: phones via libphonenumber, registrable domain, `hasWebsite`, opening hours, business status.
- Attribution, licence and terms notice on every row.
- Google `latLngCacheExpiresAt` (30-day limit).

#### Filters

- Minimum rating and minimum reviews.
- Has website, own website only, or no website.
- Has phone, open now, operational only.

#### Privacy

- Reviews (max 5, Google), reviewer names and OSM e-mails are all off by default.

#### Monetisation

- Pay per event: `osm-place` and `google-place`.
- Respects the run's maximum total charge.
- Never charges for duplicates, filtered rows or errors.

#### State and integrations

- Resumable state: completed tiles, pending split tiles, seen IDs and Google spend survive migrations.
- Export for the SiteVerdict Agency Lead Finder: key-value record `AGENCY_LEAD_FINDER_INPUT`.
