# Wongnai Scraper - Thailand Restaurants & Businesses (`haketa/wongnai-scraper`) Actor

Wongnai scraper & data API for Thailand restaurants & local businesses: search by area, cuisine or keyword and export name, category, rating, review count, price range, address, GPS, opening hours & photos. Thailand F\&B and local market data, lead generation & research — fast, no login.

- **URL**: https://apify.com/haketa/wongnai-scraper.md
- **Developed by:** [Haketa](https://apify.com/haketa) (community)
- **Categories:** Lead generation, Travel
- **Features:** Limited permissions
- **Stats:** 28 total users, 7 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.00 / 1,000 results

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

## Wongnai Scraper 🇹🇭 — Thailand Restaurants, Local Businesses, Phone, Email & GPS

[![Apify Actor](https://img.shields.io/badge/Apify-Actor-00B5AD?style=for-the-badge\&logo=apify\&logoColor=white)](https://apify.com/haketa/wongnai-scraper)
[![Target](https://img.shields.io/badge/Target-Wongnai.com-E53935?style=for-the-badge)](https://www.wongnai.com)
[![Market](https://img.shields.io/badge/Market-Thailand%20%F0%9F%87%B9%F0%9F%87%AD-1A237E?style=for-the-badge)]()
[![Lead Gen](https://img.shields.io/badge/Leads-~99%25%20Phones%20%7C%20Emails%20%7C%20LINE%20%7C%20FB-2E7D32?style=for-the-badge)]()
[![Export](https://img.shields.io/badge/Export-JSON%20%7C%20CSV%20%7C%20Excel%20%7C%20API-4A148C?style=for-the-badge)]()

**Extract Thailand restaurant and local business data from [Wongnai](https://www.wongnai.com) — Thailand's #1 lifestyle, dining, and business directory — at scale with no login and no coding.** This **Wongnai scraper** searches by **keyword, cuisine, or Thai province/city** and exports clean, structured records: **business name, branch, English & Thai categories, star rating, review count, bookmark count, price tier, phone number (~99% coverage), email address, website, LINE ID, Facebook & Instagram handles, structured opening hours, street address, sub-district (`แขวง`/`ตำบล`), district (`เขต`/`อำเภอ`), province, postal code, GPS coordinates, and high-resolution photo URLs**.

Export your Thailand B2B dataset directly to **JSON, CSV, Excel, HTML, RSS, or via the Apify API** for F\&B lead generation, POS/delivery merchant acquisition, market research, and hospitality intelligence.

***

### ⚡ At a glance

| Feature | Details |
|---|---|
| **Target platform** | [Wongnai.com](https://www.wongnai.com) — Thailand's largest restaurant & local business directory (300,000+ venues) |
| **Search modes** | **Keyword search** (Thai or English, e.g., `cafe`, `sushi`, `buffet`, `ก๋วยเตี๋ยว`), **City / province selector** (31 destinations), or **Start URLs** |
| **Contact & lead fields** | `phone` (**~98.8%** fill rate), `email` (**~59%**), `facebook` (**~58%**), `instagram` (**~43%**), `line` (**~36%**), `website` |
| **Reputation & demand** | `rating` (0–5), `numberOfReviews`, `numberOfRatings`, `numberOfBookmarks`, `numberOfPhotos`, `priceRange`, `official`, `verified` |
| **Location & GIS** | Exact `lat` / `lng` coordinates, `address`, `subDistrict`, `district`, `province`, `zipcode`, and `neighborhoods` |
| **Pagination & scale** | ~12 venues per page; unlocked multi-page crawling (`maxPagesPerQuery: 0` auto/unlimited) with 100% business `id` de-duplication |
| **Output formats** | JSON, CSV, Excel (XLSX), HTML table, RSS, and REST API |

***

### 📋 Table of contents

- [Why scrape Wongnai?](#-why-scrape-wongnai)
- [What this Wongnai scraper does](#-what-this-wongnai-scraper-does)
- [Use cases](#-use-cases)
- [Input configuration](#-input-configuration)
- [Output & field reference](#-output--field-reference)
- [Pagination & 1,000+ scale](#-pagination--1000-scale)
- [How to use](#-how-to-use)
- [Pro tips for Thailand B2B lead generation](#-pro-tips-for-thailand-b2b-lead-generation)
- [FAQ](#-faq)
- [Related scrapers](#-related-scrapers)
- [Changelog](#-changelog)

***

### 🔎 Why scrape Wongnai?

[Wongnai](https://www.wongnai.com) (part of LINE MAN Wongnai) is **Thailand's dominant local discovery and restaurant review ecosystem**, indexing hundreds of thousands of restaurants, cafés, bars, street-food stalls, bakeries, beauty salons, spas, and hotels across all 77 Thai provinces. A single search for `cafe` surfaces over **316,000 businesses across ~31,000 pages**, making Wongnai one of the richest commercial directories in Southeast Asia.

What makes Wongnai uniquely valuable for B2B sales and market intelligence is that Thai merchants actively publish their **direct phone numbers, business emails, LINE Official Account IDs (`@line`), Facebook pages, and Instagram handles** on their listings — channels that global map directories rarely capture in Thailand.

However, Wongnai offers no bulk export, paginates results 12 listings at a time, and protects pages against automated requests. This **Wongnai data extractor** handles proxy rotation, pagination, category translation, image CDN normalization, and cross-query de-duplication automatically so you get an analysis-ready dataset in minutes.

#### Key business outcomes

- 🧲 **High-converting Thailand B2B lead generation** — build targeted prospect lists of Thai restaurants, cafés, bars, and salons complete with **phone numbers (~99%)**, **emails (~59%)**, **Facebook pages (~58%)**, **Instagram (~43%)**, and **LINE IDs (~36%)**.
- 🚚 **Food delivery, POS & FinTech merchant onboarding** — identify active, high-volume venues by `numberOfReviews`, `numberOfBookmarks`, `priceRange`, and `official` status across Bangkok, Chiang Mai, Phuket, Pattaya, and regional hubs.
- 🍜 **Southeast Asia F\&B market & competitive research** — analyze cuisine saturation, price-tier distribution (`101 - 250 baht`, `251 - 500 baht`), and consumer ratings across Thai districts (`เขต`/`อำเภอ`).
- 🗺️ **Retail site selection & GIS territory mapping** — plot every competitor and neighborhood dining cluster using exact `lat` / `lng` coordinates, `subDistrict`, and `district`.
- 🏨 **Travel, tourism & hospitality enrichment** — power multilingual travel apps, hotel concierge guides, and AI trip planners with verified Thai restaurant profiles, opening hours, and high-res CDN photos.

***

### ✨ What this Wongnai scraper does

- ✅ **Bilingual keyword search (Thai & English)** — search any cuisine, dish, beverage, or venue type (`cafe`, `sushi`, `buffet`, `ramen`, `steak`, `seafood`, `ก๋วยเตี๋ยว`, `หมูกระทะ`, `คาเฟ่`) across multiple keywords in a single run.
- ✅ **Built-in Thai city & province dropdown** — filter by **Bangkok, Chiang Mai, Phuket, Chon Buri, Pattaya, Hua Hin, Rayong, Chiang Rai, Khon Kaen, Korat, Surat Thani, Krabi, Hat Yai, Nonthaburi, Samut Prakan, Ayutthaya, Udon Thani, Ubon Ratchathani**, and more — or search **All Thailand**.
- ✅ **Direct Start-URL scraping** — paste any pre-filtered Wongnai search, category, collection, or neighborhood URL into `searchUrls`.
- ✅ **Complete omni-channel contact extraction** — extracts `phone` (including multiple comma-separated numbers), `email`, `website` (normalized to `https://`), `facebook`, `line`, and `instagram`.
- ✅ **Structured weekly opening hours** — parses weekly schedules into both a structured `openingHours` array (`[{ day, from, to }]`) and a compact `openingHoursText` string (`"Mon: 08:30-23:59, Tue: 08:30-23:59..."`).
- ✅ **Direct 1920px CDN photo URLs** — resolves Wongnai's internal image placeholders into directly loadable `https://img.wongnai.com/p/1920x0/...` image URLs.
- ✅ **Unlocked 1,000+ pagination & de-duplication** — walks `page.number=1, 2, 3…` automatically (`maxPagesPerQuery: 0` auto/unlimited) and de-duplicates every business by its numeric Wongnai `id`.

***

### 🎯 Use cases

| Audience | How they use Wongnai data |
|---|---|
| **💼 B2B Sales, Wholesale & F\&B Suppliers** | Export lists of cafés, bakeries, restaurants, and bars with phone numbers, LINE IDs, Facebook links, and emails to pitch ingredients, beverage distribution, packaging, or kitchen equipment. |
| **📱 POS, Payment & Restaurant SaaS Teams** | Segment merchants by `priceRange`, `numberOfReviews`, and `district` to prioritize field-sales territories in Bangkok, Chiang Mai, and Phuket. |
| **📊 Consumer Insights & Market Researchers** | Track category growth (e.g., specialty coffee vs. Japanese dining vs. buffet chains), average ratings, and review volume across Thailand's provinces. |
| **🗺️ Real Estate & Franchise Planners** | Combine `lat`/`lng`, `neighborhoods`, and `numberOfBookmarks` to measure dining footfall before signing commercial leases. |
| **✈️ Travel Tech & OTA Platforms** | Populate Thailand destination guides with English category labels (`categories`), opening hours, price ranges, GPS pins, and high-res photos. |

***

### 📥 Input configuration

Configure your run in the Apify Console or via JSON. **Every field is optional** — leaving `queries` and `searchUrls` empty automatically runs a diverse 8-keyword Thailand food & drink sample (`cafe`, `sushi`, `buffet`, `ramen`, `steak`, `pizza`, `dessert`, `seafood`).

| Field | Type | Default | Description |
|---|---|---|---|
| `queries` | `array` | `["cafe", "sushi"]` | Search keywords in English or Thai (e.g., `"cafe"`, `"sushi"`, `"buffet"`, `"seafood"`, `"ก๋วยเตี๋ยว"`). Leave empty for an 8-keyword popular mix. |
| `region` | `string` | `""` (All Thailand) | City or province filter from the dropdown (`"1"` = Bangkok, `"373"` = Chiang Mai, `"843"` = Phuket, `"1009"` = Pattaya, `"993"` = Hua Hin, `"1036"` = Krabi, etc.). Empty = nationwide. |
| `searchUrls` | `array` | `[]` | Advanced: paste one or more Wongnai listing/search URLs (e.g., `https://www.wongnai.com/restaurants?q=ramen`) to scrape directly. |
| `maxItems` | `integer` | `0` (prefill `60`) | Maximum total businesses to collect across all queries (`0` = unlimited). |
| `maxPagesPerQuery` | `integer` | `0` | Maximum result pages to crawl per query (~12 businesses per page). Set `0` for automatic / unlimited pagination governed by `maxItems`. |
| `maxConcurrency` | `integer` | `5` | Maximum parallel page requests (`1`–`15`). |
| `proxyConfiguration` | `object` | Residential Proxy | Proxy configuration. Keep Apify **Residential** proxy enabled for reliable access across Wongnai pages. |

#### Example 1 — Bangkok café & bakery lead generation (1,000+ businesses)

```json
{
  "queries": ["cafe", "bakery", "coffee", "matcha", "bistro"],
  "region": "1",
  "maxItems": 1000,
  "maxPagesPerQuery": 0,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": ["RESIDENTIAL"]
  }
}
```

#### Example 2 — Multi-province tourist hub hospitality sweep (Phuket, Chiang Mai, Pattaya)

```json
{
  "queries": ["seafood", "thai food", "rooftop bar", "beach club"],
  "region": "843",
  "maxItems": 500,
  "maxPagesPerQuery": 0
}
```

#### Example 3 — Scrape pre-filtered Wongnai URLs directly

```json
{
  "searchUrls": [
    "https://www.wongnai.com/restaurants?q=omakase&regions=1",
    "https://www.wongnai.com/restaurants?q=shabu&regions=1"
  ],
  "maxItems": 400
}
```

***

### 📤 Output & field reference

Each scraped venue is stored as a flat, normalized JSON object in the dataset. Below is an actual record captured from a live run:

```json
{
  "id": 1448010,
  "publicId": "1448010St",
  "name": "DAVIN CAFE Davin cafe",
  "branch": null,
  "url": "https://www.wongnai.com/restaurants/1448010St-davin-cafe",
  "domain": "MAIN",
  "category": "Bakery/Cake",
  "categories": [
    "Bakery/Cake",
    "Coffee Shop/Tea House",
    "Fusion Food"
  ],
  "rating": 4.33,
  "numberOfReviews": 234,
  "numberOfRatings": 261,
  "numberOfBookmarks": 217,
  "numberOfPhotos": 892,
  "priceRange": "101 - 250 baht",
  "phone": "0918866999,0971819108",
  "email": "davincafe@davineatery.com",
  "website": "https://davincafe.com/",
  "facebook": "https://www.facebook.com/davincafethailand",
  "line": "@davincafe",
  "instagram": "davincafethailand",
  "lat": 13.82174048803,
  "lng": 100.62715978126,
  "zipcode": "10230",
  "address": "108 ถนนคลองลำเจียก แขวงนวมินทร์ เขตบึงกุ่ม กรุงเทพมหานคร 10230",
  "subDistrict": "นวมินทร์",
  "district": "บึงกุ่ม",
  "province": "Bangkok",
  "official": true,
  "premium": false,
  "verified": false,
  "ranking": null,
  "neighborhoods": [
    "เลียบทางด่วนรามอินทรา"
  ],
  "openingHours": [
    { "day": "Mon", "from": "08:30", "to": "23:59" },
    { "day": "Tue", "from": "08:30", "to": "23:59" },
    { "day": "Wed", "from": "08:30", "to": "23:59" },
    { "day": "Thu", "from": "08:30", "to": "23:59" },
    { "day": "Fri", "from": "08:30", "to": "23:59" },
    { "day": "Sat", "from": "08:30", "to": "23:59" },
    { "day": "Sun", "from": "08:30", "to": "23:59" }
  ],
  "openingHoursText": "Mon: 08:30-23:59, Tue: 08:30-23:59, Wed: 08:30-23:59, Thu: 08:30-23:59, Fri: 08:30-23:59, Sat: 08:30-23:59, Sun: 08:30-23:59",
  "photo": "https://img.wongnai.com/p/1920x0/2023/08/31/29b9120b37d8480f9f4be2aa70420a34.jpg",
  "scrapedAt": "2026-11-01T23:47:03.504Z"
}
```

#### Field reference by category

##### 🏷️ Business identity & classification

| Field | Type | Coverage | Description |
|---|---|---|---|
| `id` | `integer` | 🟢 High (100%) | Unique numeric Wongnai business ID (primary key used for de-duplication). |
| `publicId` | `string` | 🟢 High (100%) | Alphanumeric public slug ID used in Wongnai URLs (e.g., `"1448010St"`). |
| `name` | `string` | 🟢 High (100%) | Business display name (Thai, English, or bilingual). |
| `branch` | `string \| null` | 🟡 Conditional (~28%) | Specific branch or mall location name for multi-branch businesses. |
| `url` | `string` | 🟢 High (100%) | Canonical Wongnai business profile URL. |
| `domain` | `string \| null` | 🟢 High (100%) | Wongnai vertical domain tag (e.g., `"MAIN"` for restaurants/dining). |
| `category` | `string \| null` | 🟢 High (100%) | Primary business category in English (`internationalName` preferred) or Thai. |
| `categories` | `array` | 🟢 High (100%) | Complete list of cuisine/business categories assigned to the venue. |
| `official` | `boolean \| null` | 🟢 High (100%) | Whether the merchant has an official Wongnai business account. |
| `premium` | `boolean \| null` | 🟢 High (100%) | Whether the venue is a premium/sponsored listing. |
| `verified` | `boolean \| null` | 🟢 High (100%) | Whether the venue's location and details are verified by Wongnai. |

##### 📞 Contact & B2B lead-generation channels

| Field | Type | Coverage | Description |
|---|---|---|---|
| `phone` | `string \| null` | 🟢 High (~98.8%) | Callable phone number(s). Multiple numbers are comma-separated. |
| `email` | `string \| null` | 🟡 Conditional (~59%) | Direct business email address when published by the merchant. |
| `website` | `string \| null` | 🟡 Conditional (~9%) | External business website normalized to an absolute `https://` URL. |
| `facebook` | `string \| null` | 🟡 Conditional (~58%) | Facebook page URL or handle. |
| `line` | `string \| null` | 🟡 Conditional (~36%) | LINE Official Account ID (e.g., `"@davincafe"`) — the primary B2B/B2C messaging channel in Thailand. |
| `instagram` | `string \| null` | 🟡 Conditional (~43%) | Instagram username or URL. |

##### ⭐ Ratings, popularity & pricing

| Field | Type | Coverage | Description |
|---|---|---|---|
| `rating` | `number \| null` | 🟢 High (~100%) | Weighted average star rating on a 0.00–5.00 scale. |
| `numberOfReviews` | `integer \| null` | 🟢 High (100%) | Count of written user reviews. |
| `numberOfRatings` | `integer \| null` | 🟢 High (100%) | Total count of star ratings submitted. |
| `numberOfBookmarks` | `integer \| null` | 🟢 High (100%) | Number of users who saved/bookmarked the venue on Wongnai. |
| `numberOfPhotos` | `integer \| null` | 🟢 High (100%) | Total user and merchant photos uploaded to the venue profile. |
| `priceRange` | `string \| null` | 🟢 High (~97.2%) | Price tier bracket in Thai Baht (e.g., `"101 - 250 baht"`, `"251 - 500 baht"`). |
| `ranking` | `object \| null` | 🟡 Conditional | Wongnai category/area ranking metadata when assigned. |

##### 📍 Location, administrative divisions & GPS

| Field | Type | Coverage | Description |
|---|---|---|---|
| `lat` | `number \| null` | 🟢 High (100%) | WGS84 GPS latitude coordinate. |
| `lng` | `number \| null` | 🟢 High (100%) | WGS84 GPS longitude coordinate. |
| `address` | `string \| null` | 🟢 High (100%) | Street address (`ถนน`/`ซอย`). |
| `subDistrict` | `string \| null` | 🟢 High (~99%) | Thai sub-district (`แขวง` in Bangkok / `ตำบล` in provinces). |
| `district` | `string \| null` | 🟢 High (100%) | Thai district (`เขต` in Bangkok / `อำเภอ` in provinces). |
| `province` | `string \| null` | 🟢 High (100%) | Thai province (`จังหวัด`), e.g., `"Bangkok"`, `"Chiang Mai"`, `"Phuket"`. |
| `zipcode` | `string \| null` | 🟢 High (~99%) | 5-digit Thai postal code. |
| `neighborhoods` | `array` | 🟡 Conditional | Commercial neighborhood / zone tags on Wongnai. |

##### 🕒 Hours & media

| Field | Type | Coverage | Description |
|---|---|---|---|
| `openingHours` | `array` | 🟢 High (~97.8%) | Structured weekly hours array (`[{ day: "Mon", from: "08:30", to: "23:59" }, ...]`). |
| `openingHoursText` | `string \| null` | 🟢 High (~97.8%) | Single-line human-readable schedule summary for CSV/Excel exports. |
| `photo` | `string \| null` | 🟢 High (~99%) | Directly loadable 1920px CDN image URL (`https://img.wongnai.com/p/1920x0/...`). |
| `scrapedAt` | `string` | 🟢 High (100%) | ISO 8601 UTC timestamp of extraction. |

***

### 🔁 Pagination & 1,000+ scale

This **Wongnai scraper** is built to extract everything from a quick 60-venue sample to **1,000–10,000+ Thai business records** in a single run:

1. **Unlocked `maxPagesPerQuery: 0` default:** When `maxPagesPerQuery` is set to `0` (the default), the scraper automatically reads the total available page count (`tp`) reported by Wongnai for each query and steps through `page.number=1, 2, 3…` (~12 businesses per page) until `maxItems` is reached or all pages are exhausted.
2. **Honors explicit `maxItems > 100` on default runs:** Even if you leave `queries` empty to use the built-in 8-cuisine Thailand mix (`cafe`, `sushi`, `buffet`, `ramen`, `steak`, `pizza`, `dessert`, `seafood`), passing `maxItems: 1000` will automatically scale across all 8 queries and paginate deep enough to deliver all 1,000 unique businesses.
3. **100% cross-query de-duplication:** Businesses that rank for multiple keywords (e.g., both `"cafe"` and `"dessert"`) are de-duplicated in memory by their numeric Wongnai `id`, ensuring zero duplicate rows in your output.

***

### ⚙️ How to use

1. **Open the actor** in the Apify Console.
2. **Enter your `queries`** — type one or more keywords in English or Thai (e.g., `cafe`, `sushi`, `buffet`, `ก๋วยเตี๋ยว`), or paste custom URLs into `searchUrls`.
3. **Select a `region` (optional)** — pick **Bangkok**, **Chiang Mai**, **Phuket**, **Pattaya**, or any of the 31 supported destinations, or leave on **All Thailand**.
4. **Set `maxItems`** — e.g., `60` for a quick test, `1000` for a full campaign list, or `0` for unlimited.
5. **Click Start** — keep the default Residential proxy enabled.
6. **Export your dataset** — download as **CSV, Excel (XLSX), JSON, HTML, or RSS**, or connect directly to HubSpot, Google Sheets, Make, Zapier, n8n, or your data warehouse via the **Apify API**.

#### Calling via the Apify API (Node.js)

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

const client = new ApifyClient({ token: process.env.APIFY_TOKEN });

const run = await client.actor('haketa/wongnai-scraper').call({
    queries: ['cafe', 'bakery', 'rooftop'],
    region: '1', // Bangkok
    maxItems: 500,
    maxPagesPerQuery: 0,
});

const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(`Extracted ${items.length} Bangkok venues with contact data.`);
```

#### Calling via the Apify API (Python)

```python
from apify_client import ApifyClient

client = ApifyClient("YOUR_APIFY_TOKEN")

run = client.actor("haketa/wongnai-scraper").call(run_input={
    "queries": ["cafe", "sushi", "buffet", "seafood"],
    "region": "1",
    "maxItems": 600,
    "maxPagesPerQuery": 0,
})

for venue in client.dataset(run["defaultDatasetId"]).iterate_items():
    print(venue["id"], venue["name"], venue["phone"], venue["email"], venue["line"])
```

#### Popular Thai `region` IDs reference

| Region ID | Destination | Region ID | Destination |
|---|---|---|---|
| `""` | All Thailand (nationwide) | `"1036"` | Krabi |
| `"1"` | Bangkok (`กรุงเทพมหานคร`) | `"1008"` | Hat Yai (Songkhla) |
| `"373"` | Chiang Mai (`เชียงใหม่`) | `"716"` | Nonthaburi |
| `"843"` | Phuket (`ภูเก็ต`) | `"931"` | Samut Prakan |
| `"269"` | Chon Buri (`ชลบุรี`) | `"4007"` | Ayutthaya |
| `"1009"` | Pattaya (`พัทยา`) | `"1454"` | Khon Kaen |
| `"993"` | Hua Hin (`หัวหิน`) | `"2671"` | Nakhon Ratchasima (Korat) |

***

### 💡 Pro tips for Thailand B2B lead generation

- 💬 **Prioritize `line`, `facebook`, and `phone` for Thai outreach:** In Thailand, B2B decision-makers at restaurants, cafés, and salons respond fastest via **LINE Official Accounts (`line`)**, **Facebook Messenger (`facebook`)**, and **direct phone calls (`phone`)**, alongside `email` (~59% fill rate).
- 🏙️ **Segment by province for regional sales teams:** Run separate jobs with `region: "1"` (Bangkok), `region: "373"` (Chiang Mai), `region: "843"` (Phuket), and `region: "269"` (Chon Buri) so each regional sales rep receives a clean, territory-specific Excel sheet.
- 🔤 **Mix English and Thai keywords:** Wongnai matches both English (`cafe`, `seafood`, `massage`, `spas`) and Thai (`คาเฟ่`, `อาหารทะเล`, `หมูกระทะ`, `ร้านเสริมสวย`) queries. Combining both in `queries` maximizes recall while automatic ID de-duplication prevents any repeats.

***

### ❓ FAQ

#### Do I get phone numbers, emails, and LINE IDs from the search run?

Yes! Unlike platforms that hide contact details behind slow individual detail-page requests, Wongnai includes the full merchant contact block (`phone`, `email`, `website`, `facebook`, `line`, `instagram`) right inside the listing payload — so you get all contact fields at list-scraping speed.

#### Why is a Residential proxy recommended?

Wongnai protects its directory against datacenter scraping. Keeping Apify's **Residential** proxy enabled ensures high success rates and uninterrupted pagination.

#### Are categories returned in English or Thai?

Whenever Wongnai provides an `internationalName` for a category, the scraper outputs the clean **English category label** (e.g., `"Bakery/Cake"`, `"Coffee Shop/Tea House"`, `"Japanese"`, `"Seafood"`), falling back to the Thai label only if an English name is absent.

#### Do the `photo` URLs work directly in browsers and spreadsheets?

Yes. Raw Wongnai state data contains template URLs with `/p/_-x_/` placeholders that return HTTP 404 if opened directly. Our scraper automatically rewrites every image URL to `/p/1920x0/` on `img.wongnai.com` so every `photo` link loads a crisp, full-resolution image immediately.

#### How many businesses can I extract in one run?

With `maxPagesPerQuery: 0` (unlimited) and `maxItems: 1000` (or `0`), you can extract **thousands of unique Thai businesses** in a single run by combining several keywords or provinces.

***

### 🔗 Related scrapers

Expanding your F\&B, hospitality, or APAC local-business data pipeline? Check out our related extractors:

- 🇰🇷 [Naver Place Scraper](https://apify.com/haketa/naver-place-scraper) — South Korea's #1 local business & restaurant directory.
- 🍔 [DoorDash Scraper](https://apify.com/haketa/doordash-scraper) — Restaurant listings, menus, ratings, and delivery fees from DoorDash.
- 🍕 [Grubhub Scraper](https://apify.com/haketa/grubhub-scraper) — US restaurant profiles, menus, and pricing from Grubhub.
- 🥡 [Just Eat Scraper](https://apify.com/haketa/just-eat-scraper) — European & UK restaurant and takeaway listings from Just Eat.

***

### 📋 Changelog

#### v1.2 (2026-11)

- **Unlocked 1,000+ deep pagination:** Changed `maxPagesPerQuery` default from `10` to `0` (automatic/unlimited, governed by `maxItems`), removed the `200`-page schema cap, and fixed default-query runs so explicit `maxItems > 100` values are always honored without clamping to 100.
- **Fast prefill & schema improvements:** Set `maxItems` prefill to `60` for rapid test runs, added output schema descriptions, and expanded documentation with field coverage benchmarks.

#### v1.1 (2026-10)

- **Full B2B contact & hours normalization:** Added `email`, `website` (auto-prefixed with `https://`), `facebook`, `line`, `instagram`, structured `openingHours` + `openingHoursText`, and loadable `1920x0` CDN `photo` URLs.

#### v1.0 (2026-05)

- Initial release supporting Thailand keyword search, 31-region dropdown selector, and Start-URL scraping.

# Changelog

This Actor's version history is a separate document: https://apify.com/haketa/wongnai-scraper/changelog.md

# Actor input Schema

## `queries` (type: `array`):

What to look for on Wongnai — a cuisine, dish, or business type (Thai or English). Add one or more, e.g. cafe, sushi, buffet. Leave empty to get a ready-made mix of popular Thailand food & drink spots.

## `region` (type: `string`):

Limit results to one city or province. Choose a popular destination below, or leave on 'All Thailand' to search the whole country.

## `searchUrls` (type: `array`):

Optional. Paste one or more Wongnai listing pages (a search, cuisine or area page) to scrape them directly. Most users can leave this empty and use the search keywords and city picker above.

## `maxPagesPerQuery` (type: `integer`):

How deep to paginate each search (about 12 businesses per page). Set 0 for automatic / unlimited pagination (governed by Max businesses).

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

Maximum number of businesses to collect. Set 0 for no limit.

## `maxConcurrency` (type: `integer`):

Maximum parallel page requests.

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

For reliable results at scale, keep the recommended residential proxy (Thailand works best).

## Actor input object example

```json
{
  "queries": [
    "cafe",
    "sushi"
  ],
  "region": "",
  "maxPagesPerQuery": 0,
  "maxItems": 60,
  "maxConcurrency": 5,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ]
  }
}
```

# Actor output Schema

## `businesses` (type: `string`):

All Thailand restaurant and local business records collected from Wongnai.

# 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 = {
    "queries": [
        "cafe",
        "sushi"
    ],
    "maxItems": 60,
    "proxyConfiguration": {
        "useApifyProxy": true,
        "apifyProxyGroups": [
            "RESIDENTIAL"
        ]
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("haketa/wongnai-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 = {
    "queries": [
        "cafe",
        "sushi",
    ],
    "maxItems": 60,
    "proxyConfiguration": {
        "useApifyProxy": True,
        "apifyProxyGroups": ["RESIDENTIAL"],
    },
}

# Run the Actor and wait for it to finish
run = client.actor("haketa/wongnai-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 '{
  "queries": [
    "cafe",
    "sushi"
  ],
  "maxItems": 60,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ]
  }
}' |
apify call haketa/wongnai-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,haketa/wongnai-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/JTUfdBLlXuZQCw6h8/builds/5VVSBhullfGii9BPT/openapi.json
