# Search for attractions 3.2 Beta

**Learn how to use the /attractions/search endpoint to find and retrieve attractions that match travellers’ preferences, locations, and travel dates.**

→ Use the [/attractions/search endpoint](/demand/docs/open-api/3.2-beta/demand-api/attractions/search) to retrieve a list of available attractions, activities, and experiences based on a search criterion, travel dates, and optional filters.

This endpoint returns **real-time availability and up-to-date prices** for our travel experiences inventory.

If you store our attractions inventory retrieved from orders/details endpoint, use the /attractions/search endpoint to retrieve live availability and the latest prices before displaying them to travellers.

## Minimum request example

The smallest valid request must include:

* A location search criterion
* Currency
* Dates


Example:


```json
{
  "currency": "EUR",
  "cities": [-2140479, -2154955],
  "dates": {
    "start_date": "2026-09-18",
    "end_date": "2026-09-20"
  }
}
```

Optional parameters such as `filters`, `rows`, and `sort`

## How it works

A **search request** defines the parameters used to find attractions. The **response** returns a list of matching attractions and metadata describing the result set.

Example scenario:

> *Retrieve attractions in the Netherlands and Belgium available between 18–20 September 2026, filtered by minimum review score and supported languages.*



```json
{
  "currency": "EUR",
  "countries": ["nl", "be"],
  "dates": {
    "start_date": "2026-09-18",
    "end_date": "2026-09-20"
  },
  "filters": {
    "rating": {
      "minimum_review_score": 4.2,
      "minimum_review_count": 100
    },
    "supported_languages": ["en", "es", "fr", "de"]
  },
  "rows": 50,
  "sort": {
    "by": "most_popular"
  }
}
```

## Search input

The request body defines **where and how to search for attractions**.

### Required fields

| Field | Required | Format | Description |
|  --- | --- | --- | --- |
| `currency` | Yes | ISO 4217 code (e.g. `EUR`) | Currency used for pricing in the response. |
| `dates.start_date` | Yes | `YYYY-MM-DD` | Start of the availability period. |
| `dates.end_date` | Yes | `YYYY-MM-DD` | End of the availability period. |


`start_date` must be before or equal to `end_date`.

#### Location search criteria

You must include **one of the following fields** to define where to search for attractions.

| Field | Format | Restriction | Description |
|  --- | --- | --- | --- |
| `attractions` | Array of strings (attraction IDs) | Maximum 100 attraction IDs | Retrieve specific attractions using attraction IDs. |
| `cities` | Array of integers (city IDs) | Maximum 5 cities. | Search for attractions located in one or more cities. |
| `countries` | Array of strings (ISO country codes) | Maximum 3 countries. | Search for attractions within specific countries. |
| `coordinates` | Object (`latitude`, `longitude`, optional radius) |  | Search for attractions near a geographic location. |


**Example (city search):**


```json
{
  "currency": "EUR",
  "cities": [-2140479],
  "dates": {
    "start_date": "2026-09-18",
    "end_date": "2026-09-20"
  }
}
```

### Optional fields

#### Key filters

Filters allow you to restrict the search to specific criteria. You can use one or more filters in the same request.

* `filters.categories` – Filter by attraction type
* `filters.rating` – Filter by review score and count
* `filters.supported_languages` – Filter by supported languages


##### Categories

Use `filters.categories` to filter results by type of attraction.

**Example of filter by categories request:**


```json
{
  "currency": "EUR",
  "countries": ["nl"],
  "dates": {
    "start_date": "2026-06-18",
    "end_date": "2026-06-20"
  },
  "filters": {
    "categories": ["PTTV32SGqJEv"]
  }
}
```

Supported categories include:

| Category | ID |
|  --- | --- |
| Tours | `PTTV32SGqJEv` |
| Services and rentals | `PTTV3YDywxmN` |
| Workshops and classes | `PTTV3bWrrud5` |
| Museums, arts and culture | `PTTV3cuXCgPo` |
| Nature and outdoor | `PTTV3jCHmADM` |
| Entertainment and tickets | `PTTV3t1Fvjp9` |
| Food and drink | `PTTV3y2qdlBL` |


* You can provide multiple category IDs. Results include attractions that match **any** of the selected categories.


If an invalid or unsupported category ID is provided, the response will return no results.

##### Reviews

You can filter by review score and total count.

| Field | Format | Description |
|  --- | --- | --- |
| `filters.rating.minimum_review_score` | Number (0–5) | Minimum average guest review score. |
| `filters.rating.minimum_review_count` | Integer ≥0 | Minimum number of guest reviews. |


##### Supported languages

Use `filters.supported_languages` to filter results by the languages supported by the attraction (IETF language tags).


```json
"filters": {
  "supported_languages": ["en", "de"]
}
```

#### Multiple filters example

Filters allow you to refine results based on **quality indicators and traveller preferences**.


```json
"filters": {
  "categories": ["PTTV32SGqJEv"]
  "rating": {
    "minimum_review_score": 4.0,
    "minimum_review_count": 50
  },
  "supported_languages": ["en", "de"]
}
```

### Paginate and sort results

* Use `rows` to set the number of results returned per page.
* Use `page` as pagination token returned in `metadata.next_page`.
* Use `sort.by` to control how attractions results are ordered.


| Sort option | Description |
|  --- | --- |
| `most_popular` | Orders products by the highest number of reservations in the last 30 days. |
| `highest_review_score` | Shows attractions with the highest average review score first. |
| `highest_weighted_review_score` | Orders attractions by a weighted review score combining rating and review volume. |
| `lowest_price_first` | Displays attractions with the lowest available price first. |
| `nearest_location` | When using the `coordinates` search criterion, it displays products closest to the provided search coordinates first. |
| `trending` | Orders attractions based on predicted popularity using machine learning signals. |


**Pagination and sorting example**


```json
"rows": 50,
"sort": {
  "by": "lowest_price_first"
},
"page": "eyJhbGciOiJIUzI1NiJ9..."
```

See the [pagination guide](/demand/docs/development-guide/pagination) for details.

## Response

The response returns:

* Matching attractions.
* Pagination metadata.
* A unique request identifier.



```json
{
  "data": [
    {
      "id": "PRahAzWtTraa",
      "free_cancellation": true,
      "price": {
        "currency": "EUR",
        "total": 20
      },
      "urls": {
        "app": {
          "detail": "booking://attractions/product?slug=prahazwttraa-heineken-experience-amsterdam&aid=956509",
          "search_results": "booking://attractions/searchresults?ufi=-2140479&pinned_product_id=PRahAzWtTraa&aid=956509"
        },
        "web": {
          "detail": "https://www.booking.com/attractions/nl/prahazwttraa-heineken-experience-amsterdam.en-gb.html?selected_currency=EUR&aid=956509",
          "search_results": "https://www.booking.com/attractions/searchresults/nl/amsterdam.en-gb.html?pinned_product=PRahAzWtTraa&aid=956509"
        }
      }
    },
    {
      "id": "PRAmdacCwQLH",
      "free_cancellation": false,
      "price": {
        "currency": "EUR",
        "total": 15.5
      },
      "urls": {
        "app": {
          "detail": "booking://attractions/product?slug=pramdaccwqlh-madame-tussauds-ticket&aid=956509",
          "search_results": "booking://attractions/searchresults?ufi=-2140479&pinned_product_id=PRAmdacCwQLH&aid=956509"
        },
        "web": {
          "detail": "https://www.booking.com/attractions/nl/pramdaccwqlh-madame-tussauds-ticket.en-gb.html?selected_currency=EUR&aid=956509",
          "search_results": "https://www.booking.com/attractions/searchresults/nl/amsterdam.en-gb.html?pinned_product=PRAmdacCwQLH&aid=956509"
        }
      }
    }
  ],
  "metadata": {
    "next_page": "eyJhbGciOiJIUzI1NiJ9...",
    "total_results": 128
  },
  "request_id": "01fr9ez700exycb98w90w5r9sh"
}
```

#### When no results are returned

If no attractions are returned:

* Verify that the **date range** has available inventory.
* Check whether **filters are too restrictive**.
* Confirm that **city or country IDs are valid**.


If necessary, broaden the search criteria or remove filters temporarily.

Products coverage
Not all attractions or experiences visible on the Booking.com website are available via the Demand API. The API intentionally provides a curated subset of experiences designed for partner integrations and connected travel solutions.

## Typical integration flow

Most integrations use /attractions/search as part of the following workflow:

1. Retrieve location identifiers from /common/locations endpoints.
2. Search for attractions using /attractions/search.
3. Display results to travellers.
4. Retrieve full product information with /attractions/details.
5. Continue with availability and booking flows.


## Best practices

✅ Optimise performance:

* Limit `rows` to **20–50 results** for faster responses.
* Use **pagination tokens** instead of fetching all data at once.


✅ Improve result relevance:

* Combine **location-based search** (coordinates) and qualitative filters.
* Select `sort.by` according to the traveller’s goal, such as `most_popular` for discovery or `lowest_price_first` for value.


✅ Maintain integration efficiency

* Always include **currency and travel dates**.
* Store location IDs from [/common/locations endpoints](/demand/docs/open-api/3.2-beta/demand-api/commonlocations/) and previously retrieved attraction lists to minimise repeated lookups and API calls.


Curious to know more?
- Refer to the [Search use cases section](/demand/docs/attractions/search-attractions-examples) for more examples.
- Read the [Attraction details guide](/demand/docs/attractions/retrieve-attraction-details) to learn how to obtain attraction static data.
- See the [Pagination guide](/demand/docs/development-guide/pagination) for instructions on paginating search results.