Viator Scraper – Tours, Activities, Prices & Availability avatar

Viator Scraper – Tours, Activities, Prices & Availability

Pricing

from $1.50 / 1,000 results

Go to Apify Store
Viator Scraper – Tours, Activities, Prices & Availability

Viator Scraper – Tours, Activities, Prices & Availability

Collect Viator.com tour and activity results from destinations, categories, search pages, or pasted URLs. Returns product codes, prices, ratings, reviews, images, availability, source context, and optional detail fields.

Pricing

from $1.50 / 1,000 results

Rating

0.0

(0)

Developer

Abot API

Abot API

Maintained by Community

Actor stats

1

Bookmarked

13

Total users

3

Monthly active users

5 days ago

Last modified

Share

Viator Scraper: Tours, Activities, Prices and Ratings

Viator Scraper turns Viator into structured travel data. Get tour and activity listings for seven major destinations and six tour categories, including prices, ratings, review counts, availability, images and source breadcrumbs, plus optional full product page detail with descriptions, complete image lists, recent reviews and itinerary stops. Pick a destination and category, or paste Viator listing URLs, then export to JSON, CSV or Excel, or pull results straight into your app through the API.

Why This Scraper?

  • Two ways to find data. Pick a destination and category preset (7 destinations, 6 categories), or paste Viator destination, category or search-result listing URLs directly. No need to build URLs by hand.
  • Filters and sort work everywhere. Keyword, price range, currency, minimum rating, minimum reviews and availability all narrow and reorder results in both search mode and URL mode, including a pasted URL's results.
  • Optional detail enrichment. Turn on Fetch details to open each product's own page for its full description, complete image list, up to 10 recent reviews and itinerary stops. Rows are still saved when a product page can't be opened.
  • Nothing lost on a failed run. Every matching row is written to the dataset as soon as it's found, so a run that stops partway through still keeps what it already collected.
  • Deduplicated pagination. Listing pages are walked until Max items is reached or a page repeats an earlier page's results, and the same product is never saved twice.
  • Cost control built in. Max items and Max pages cap a run before it starts, and detail enrichment is billed only for the product pages that are successfully enriched.

Use Cases

  • Travel research and itinerary planning: compare tours and activities in a destination by price, rating and availability before booking.
  • Price and catalog monitoring: track how listed prices, availability and review counts for a set of products change over time.
  • Market research for tour operators: see how bus tours, walking tours, day trips and attractions in a destination are priced and reviewed.
  • Content and affiliate sites: pull activity names, images, descriptions and ratings to build destination guides or comparison pages.
  • Outreach and lead lists: collect tour and operator names with source context for a destination or category to prioritize outreach.

Data You Get

Sample shape: values are illustrative placeholders, not from a live record.

FieldExample
name"Boston Hop-On Hop-Off Trolley Tour"
productCode"5892HOHO"
urlViator link to the activity
imageMain image URL
locationName"Boston" (destination name parsed from page context, when available)
addressLocality"Boston" (locality parsed from page context, when available)
addressCountryName"United States" (parsed from the page's breadcrumb, when available)
offerPrice / offerCurrency42.5 / "USD"
availability"InStock"
priceValidUntil"2027-01-01" (when present)
ratingValue / exactRating4.6 / 4.6 (both read from the same source rating)
bestRating / worstRating5 / 1
reviewCount1280
descriptionfull activity description (when Fetch details is on)
imagesall product image URLs (when Fetch details is on)
reviewsup to 10 recent reviews with author, rating, date and text (when Fetch details is on)
itineraryStopCount / itineraryStopsstop count and stop names (when Fetch details is on)
positionposition on the source listing page
sourceUrl / sourcePagelisting page URL and page number the row came from
sourceName / sourceDescriptionlisting page title and description text
breadcrumbslisting page breadcrumb labels
detailStatus"not_requested", "enriched", "no_structured_detail", or "unavailable"
detailErrordetail fetch error summary (only when Fetch details fails for that row)
scrapedAtISO timestamp

Every row is a tour or activity listing; there is no separate record type. description, images, reviews, itineraryStopCount and itineraryStops are only populated when Fetch details is switched on, and only for the rows whose product page loaded successfully.

How to Use

  1. Pick a mode: search (destination and category preset) or url (paste Viator listing links).
  2. Fill in the fields for that mode: destination and category for search mode, or one or more listing URLs for URL mode.
  3. Optionally set keyword, price, currency, rating, review and availability filters, choose a sort order, and turn on Fetch details for full product pages.
  4. Set Max items and Max pages to control run size and cost, then click Start.

Search Boston bus tours, filtered and sorted:

{
"mode": "search",
"destination": "boston",
"category": "bus_tours",
"keyword": "hop",
"minRating": 4,
"minReviews": 50,
"sortBy": "price_asc",
"maxItems": 20,
"maxPages": 0
}

Search with detail enrichment:

{
"mode": "search",
"destination": "paris",
"category": "walking_tours",
"fetchDetails": true,
"maxItems": 10,
"maxPages": 1
}

Paste a listing URL, filters still apply:

{
"mode": "url",
"urls": ["https://www.viator.com/Boston-tours/Bus-and-Minivan-Tours/d678-g12-c98"],
"currency": "USD",
"minRating": 4,
"sortBy": "rating_desc",
"maxItems": 20
}

URL mode with a price range:

{
"mode": "url",
"urls": ["https://www.viator.com/London-tours/Tours-and-Sightseeing/d737-g12"],
"minPrice": 30,
"maxPrice": 150,
"maxItems": 30,
"maxPages": 0
}

Run it from your code

Python:

from apify_client import ApifyClient
client = ApifyClient("<YOUR_APIFY_TOKEN>")
run = client.actor("abotapi/viator-com-scraper").call(
run_input={"mode": "search", "destination": "boston", "category": "bus_tours", "maxItems": 20}
)
for row in client.dataset(run["defaultDatasetId"]).iterate_items():
print(row["name"], row["offerPrice"], row["offerCurrency"])

JavaScript:

import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: '<YOUR_APIFY_TOKEN>' });
const run = await client.actor('abotapi/viator-com-scraper').call({
mode: 'search',
destination: 'boston',
category: 'bus_tours',
maxItems: 20,
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();

Or connect it to Make, Zapier, n8n, Google Sheets or webhooks from the Integrations tab.

Send results into your apps (MCP connectors)

Optionally pipe a capped subset of saved rows into the apps you already use, via Model Context Protocol (MCP) connectors. This is an extra delivery step after the scrape: the Apify dataset is never changed.

What gets written to the connector: a condensed, human-readable summary of each row, not the full JSON. Each row becomes one entry with a title and its key fields flattened to plain text. The complete record always stays in the Apify dataset.

  1. Authorize a connector once under Apify → Settings → Integrations (Notion, Linear, Airtable, or Apify).
  2. Select it in the "Pipe results into your apps" input field. (If the picker is empty, you haven't authorized a connector yet.)
  3. For Notion, also set notionParentPageUrl to the page where rows should be created.

The connection is mediated by Apify's MCP proxy, so this actor never sees your third-party credentials. Leave the field empty to skip.

Input Parameters

ParameterTypeDefaultDescription
modestringsearchsearch (destination/category preset) or url (pasted listing URLs).
destinationstringbostonDestination preset: Boston, New York City, Las Vegas, London, Paris, Rome, or Sydney. Search mode only; ignored in URL mode.
categorystringtours_sightseeingCategory preset: Tours and sightseeing, Bus tours, Day trips, Walking tours, Food and drink, or Attractions and tickets. Search mode only; ignored in URL mode.
urlsarraynone (prefill: sample Boston listing URL)Viator destination, category or search-result listing URLs for URL mode.
keywordstringnoneText that must appear in the activity name, URL, destination or category text. Applies in both modes, including a pasted URL.
minPricenumbernoneMinimum listed price. Both modes.
maxPricenumbernoneMaximum listed price. Both modes.
currencystringAnyKeep only rows in a selected currency. Both modes.
minRatingnumbernoneMinimum aggregate rating. Both modes.
minReviewsintegernoneMinimum review count. Both modes.
availabilitystringAnyAvailability filter. Both modes.
sortBystringsourceSource, price, rating, or review-count order. Both modes; applied per page of results as it is saved.
fetchDetailsbooleanfalseOpen each product page for description, all images, reviews and itinerary. Results are still saved if a product page is unavailable.
maxItemsinteger20Maximum matching rows to save (at least 1). Fewer rows can be returned when the source and filters match fewer live records.
maxPagesinteger0No page limit when set to 0. The run stops at Max items.
proxyobjectResidential (Apify Proxy)Connection settings.
mcpConnectorsarraynoneOptional: send a summary of each saved row to apps you authorized under Integrations.
notionParentPageUrlstringnoneNotion connector only: page under which rows are created.
maxNotifyListingsinteger50Cap on rows written to each connector per run (1-1000). Does not affect the dataset.

Output Example

Sample shape: values are illustrative placeholders, not from a live record.

{
"name": "Boston Hop-On Hop-Off Trolley Tour",
"productCode": "5892HOHO",
"url": "https://www.viator.com/tours/Boston/Old-Town-Trolley-Tour/d678-5892HOHO",
"image": "https://media.viator.com/sample-image-1.jpg",
"locationName": "Boston",
"addressLocality": "Boston",
"addressCountryName": "United States",
"offerPrice": 42.5,
"offerCurrency": "USD",
"availability": "InStock",
"priceValidUntil": "2027-01-01",
"ratingValue": 4.6,
"exactRating": 4.6,
"bestRating": 5,
"worstRating": 1,
"reviewCount": 1280,
"description": "Hop on and off a narrated trolley at stops around Boston's historic sites.",
"images": [
"https://media.viator.com/sample-image-1.jpg",
"https://media.viator.com/sample-image-2.jpg"
],
"reviews": [
{ "author": "Sample Traveler", "rating": 5, "date": "2025-06-01", "text": "Great way to see the city." }
],
"itineraryStopCount": 3,
"itineraryStops": ["Faneuil Hall", "Boston Common", "North End"],
"position": 3,
"sourceUrl": "https://www.viator.com/Boston-tours/Bus-and-Minivan-Tours/d678-g12-c98",
"sourcePage": 1,
"sourceName": "Boston Bus and Minivan Tours",
"sourceDescription": "Bus and minivan tours in Boston.",
"breadcrumbs": ["Home", "Things to do in United States", "Boston", "Bus and Minivan Tours"],
"detailStatus": "enriched",
"scrapedAt": "2026-09-28T12:00:00.000000+00:00"
}

Plan Requirement

This actor bills per saved result, plus a small start charge per run and, when Fetch details is switched on, a charge for each product page that is successfully enriched. The Pricing tab shows current rates. Residential proxy is selected by default; it is recommended for this site, since other proxy groups can return fewer usable pages or get blocked.

FAQ

How much does it cost?

You pay a small start charge per run and a fee per saved result, plus a detail-enrichment charge for each row that is successfully enriched when Fetch details is on. The Pricing tab shows current rates. Use Max items and Max pages to cap the cost of a run.

This actor collects only publicly available tour and activity listings. You are responsible for how you use it: follow Viator's terms and the laws that apply to you, and get legal advice if you plan commercial redistribution. Reviews, photos and descriptions may be subject to third-party rights.

Do the filters and sort also apply when I paste a URL?

Yes. Keyword, price range, currency, minimum rating, minimum reviews, availability and sort order all apply to search mode and to a pasted URL's results alike. Only Destination and Category are search-mode presets; they pick the listing page that search mode walks and are ignored in URL mode, where the pasted URL is the source instead.

Can I schedule recurring runs, or get only new results?

You can schedule the actor from the Schedules tab to run automatically, but each run collects matching rows from scratch. There is no built-in incremental or resume mode that skips rows a previous run already returned; deduplicate on productCode on your side if you run this repeatedly against the same source.

Why did my run return 0 rows instead of an error?

URL mode needs at least one URL: if Mode is url and no URL is provided, the run completes with an empty dataset. A destination and category combination, or a keyword and filter set, with no matching live listings can also legitimately return 0 rows.

Why did my run fail instead of returning an empty dataset?

If a listing page can't be loaded at all, even after retries and one proxy session rotation, the run stops with an error rather than reporting an empty result as if nothing was there. Rows already saved before the failure stay in the dataset. Try again, or switch the proxy group under Connection to residential.

Paste a Viator destination, category or search-result listing URL, a page that shows a list of tours. A standalone product page on its own does not produce a row for that product; turn on Fetch details instead to pull full product-page fields (description, all images, reviews, itinerary) for the rows already found on a listing page.

Can I use it with AI agents or MCP?

Yes. Call it from any Apify integration or MCP client, and use the connector field to push a summary of saved rows into Notion, Linear or Airtable.

🔗 Want more travel data?

Pair this actor with these related scrapers from the same team:

🧩 KKday Scraper
Scrape KKday travel activities by keyword, city or URL. Every row carries prices...
🏨 Klook Scraper
Scrape Klook activities, tours, attractions and travel experiences from search pages or...
🛒 Costco AU Scraper
Scrape Costco.com.au products with full details and customer reviews. Search by keyword...
✈️ Naver Map Scraper
From $1/1K. Scrape Naver Map places by keyword or URL: names, categories, ratings...
🛒 Idealo.de
Scrape Idealo.de products with identity details, GTIN, price ranges, specifications...
✈️ FurnishedFinder
From $1/1K. Scrape furnishedfinder.com listings by city or URL. Extract structured data...

👉 Browse all abotapi scrapers

💬 Support & custom scrapers

  • 🐞 Found a bug or a missing field? Open a ticket on the Issues tab. We usually reply within hours.
  • 🛠️ Need another site, extra fields or a private build? Email abotapi@proton.me or message Telegram @abotapi.
  • ⭐ Enjoying it? A quick review on the actor page helps other users find it.