# EaseMyTrip Hotels Scraper - Prices, Ratings, Locations (`bovi/easemytrip-scraper`) Actor

Collect public hotel records from EaseMyTrip. Get name, INR price, rating, address, coordinates, check-in and check-out times and amenities. Run with a listing URL, hotel page or sitemap; no EaseMyTrip login. Pricing: $0.0035 per hotel record and $0.00005 per Actor start on Free.

- **URL**: https://apify.com/bovi/easemytrip-scraper.md
- **Developed by:** [Vitalii Bondarev](https://apify.com/bovi) (community)
- **Categories:** Travel, Lead generation
- **Features:** Limited permissions
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $3.50 / 1,000 easemytrip hotels scraper - prices, ratings, locations

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

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

## EaseMyTrip Hotels Scraper: Prices and Ratings

Scrape public hotel pages on EaseMyTrip for name, the INR price shown, rating, address, coordinates, check-in and check-out times, main photo and amenities, with no login. Pay per event on the Free plan: $0.0035 per hotel record delivered and $0.00005 per Actor start.

- Compare the INR price and rating shown for hotels on one city or category listing.
- Build a hotel lead list from name, street address, coordinates and amenities.
- Collect one public hotel page, or hotel URLs found in a sitemap, in the same run.
- A price the site does not show, and any other unpublished field, comes back as null.
- An Apify account is enough; the Actor does not ask for an EaseMyTrip login or API key.

### What you get

Each dataset item is one hotel. Values come from the public JSON-LD on the hotel page (`LodgingBusiness` or `Hotel`). `amenities` is always an array. Every other field that the page does not publish is null.

| Field | Type | Description |
| --- | --- | --- |
| id | string | EaseMyTrip hotel id, the numeric suffix of the hotel URL |
| url | string | Hotel page URL on easemytrip.com |
| name | string | Hotel name |
| rating | number or null | Rating on a 0–5 scale as published in the page structured data |
| price_inr | number or null | Price shown by the site for the hotel, in INR; null when the site shows none |
| currency | string or null | Currency of price_inr; INR when a price is present, otherwise null |
| city | string or null | City from the page breadcrumb |
| address | string or null | Street address |
| region | string or null | State or region |
| postal_code | string or null | Postal code |
| country_code | string or null | ISO country code |
| latitude | number or null | Latitude |
| longitude | number or null | Longitude |
| check_in_time | string or null | Check-in time |
| check_out_time | string or null | Check-out time |
| image_url | string or null | Main photo URL |
| amenities | array | Amenity names listed on the page |
| listing_url | string or null | Listing page the hotel was found on |
| scraped_at | string | UTC timestamp of the scrape |

> **Note:** `price_inr` is the price the site shows at the moment of the scrape, not a fixed room rate. `rating` is the value published in the page data.

### Sample output

One hotel record from a run that started at the public Goa hotels listing. All fields from that record are included.

```json
{
  "id": "1099685",
  "url": "https://www.easemytrip.com/hotels/the-baga-beach-resort-1099685/",
  "name": "The Baga Beach Resort",
  "rating": 4.2,
  "price_inr": 9499,
  "currency": "INR",
  "city": "Goa",
  "address": "7/225/A, Saunta Vaddo, Baga, Calangute, Goa 403516",
  "region": "GOA",
  "postal_code": "403516",
  "country_code": "IN",
  "latitude": 15.556173393, "longitude": 73.752193027,
  "check_in_time": "02:00 PM",
  "check_out_time": "11:00 AM",
  "image_url": "https://img.easemytrip.com/EMTHOTEL-1099685/70/32/na/s/39591428_0.jpg",
  "amenities": ["Gym", "Swimming Pool", "Restaurant", "Bar"],
  "listing_url": "https://www.easemytrip.com/hotels/hotels-in-goa/",
  "scraped_at": "2026-10-15T01:30:49.596057+00:00"
}
```

### Pricing

Billing is pay per event. Two Free-plan events are charged:

| Event | When it is charged | Free-plan price |
| --- | --- | --- |
| `apify-default-dataset-item` | One scraped hotel record with all fields | $0.0035 |
| `apify-actor-start` | When the Actor starts. One event per GB of memory, minimum one event | $0.00005 |

1,000 hotel records cost $3.5 on Free and 10,000 hotel records cost $35 on Free. 1,000 Actor starts cost $0.05 on Free and 10,000 Actor starts cost $0.5 on Free.

Default memory is 512 MB, so a default run is one Actor start ($0.00005 on Free). 1428 hotel records plus that one start = $4.99805 on Free, which fits inside the $5 monthly platform credit of the Apify Free plan.

Platform usage for compute, Apify Proxy traffic including residential, and storage is included in these event prices and is paid by the Actor developer. It is not a separate charge on your run.

### How to use

1. Open the Actor in Apify Console with your own Apify account.
2. Set `startUrls` to a city or category listing, one hotel page, or a hotel sitemap XML URL.
3. Set `maxResults` to the number of named hotels you want to save.
4. Choose `proxyConfiguration`, then start the run with input in this shape.

```json
{
  "startUrls": [{ "url": "https://www.easemytrip.com/hotels/hotels-in-goa/" }],
  "maxResults": 50,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": ["RESIDENTIAL"]
  }
}
```

5. Open the dataset after the run; only hotels that have a name are stored.
6. Repeat the run through Apify Schedules. Daily is a starting point for hotel prices.

Export the dataset as JSON or CSV, or read it through the Apify dataset API.

### Input parameters

| Parameter | What it does | Default |
| --- | --- | --- |
| startUrls | Required in the input form. Each entry is fetched once. A hotel page contributes that hotel. A `.xml` sitemap contributes hotel URLs from at most 20 sitemap files. Any other URL is treated as a listing, and hotel links on that page are collected. The same hotel URL is kept once. If the list is empty, the run uses the Goa listing shown in the Default column. | `https://www.easemytrip.com/hotels/hotels-in-goa/` |
| maxResults | Maximum number of hotel records with a name to save. A value below 1 saves nothing; an invalid value falls back to 50. | 50 |
| proxyConfiguration | When this object is set and `useApifyProxy` is not false, fetches use Apify Proxy with the groups you pass. Set `useApifyProxy` to false to fetch with no proxy. The site is reachable without a proxy from most IPs; turn the proxy on if you get blocked. | Apify Proxy, group `RESIDENTIAL` |

### Limits and edge cases

Each hotel page is fetched once, five pages at a time, so runtime grows with `maxResults`. A URL is tried up to four times with a 40-second timeout per try. Flights, trains, buses and logged-in areas are out of scope.

| Condition | What you see | What to do |
| --- | --- | --- |
| Saved hotels reach maxResults | The dataset stops at that many hotels that have a name | Raise maxResults |
| The listing has fewer hotel links than maxResults | Fewer records than maxResults | Add another listing URL, a hotel URL, or a sitemap |
| Many queued pages have no hotel name | The dataset can end below maxResults, because at most twice maxResults hotel URLs are queued | Add another start URL |
| You expect the next listing page | Only links on the fetched page are used; further listing pages are not followed | Put each listing page you need in startUrls |
| Sitemap input | At most 20 XML files are read. Reading stops once maxResults hotel URLs have already been gathered; the last file can add more, still subject to the queue cap | Point startUrls at the sitemap file you want |
| HTTP 404 or 410 | That URL is skipped and adds no row | Correct the URL |
| Page has no LodgingBusiness or Hotel JSON-LD, or no name | No dataset row for that page. Rows already saved stay | Use a public hotel detail page |
| Fetch still fails after four tries | That source or hotel is skipped. The log says the source could not be read, or the hotel fetch failed. Rows already saved stay | Run again. If direct requests fail, set useApifyProxy to true with the RESIDENTIAL group |
| No price, or the parsed price is not above zero | price_inr and currency are null | Expected when the site shows no price |
| Coordinates are missing, or both are 0 | latitude and longitude are null | Expected when the site has no coordinates |
| startUrls is a single hotel page | listing_url is null for that hotel | Start from a listing or a sitemap if you need listing_url |

### FAQ

#### How much does it cost to scrape EaseMyTrip hotels?

You pay to extract each hotel the Actor delivers: one `apify-default-dataset-item` event per hotel record, plus one `apify-actor-start` event per GB of memory (one at the default 512 MB). The Free-plan prices, the worked example and the $5 credit are in the Pricing section.

#### Why is the dataset empty?

The start URL returned no hotel links, every hotel page lacked a name or hotel JSON-LD, every fetch failed, or maxResults was below 1. Check that each URL is a public city or category listing, a hotel page, or a hotel sitemap. Then set maxResults to at least 1 and read the run log for how many hotel pages were found.

#### What happens when a hotel page fails?

A 404 or 410 is skipped. Any other fetch error is retried up to four times and then that URL is skipped. Hotels already written to the dataset stay there. The run log reports a failed source or a failed hotel fetch, then the number of hotels saved.

#### Do I need an EaseMyTrip login to scrape?

No. You do not provide an EaseMyTrip login, cookies, or an API key. Export the dataset as JSON or CSV after the run. Proxy use is optional: the schema default is Apify Proxy with the RESIDENTIAL group, and `useApifyProxy` false fetches with no proxy.

#### Is it allowed to collect this public hotel data?

The Actor reads public hotel pages and the structured data on those pages. It does not sign in. Whether that is allowed depends on EaseMyTrip's terms and on the law that applies to your use case. Nothing here is a legal ruling on your use.

### Related actors

- [OpenTable Scraper — Reviews, Restaurants & Availability](https://apify.com/bovi/opentable-scraper) — public restaurant, review and availability data from bovi.
- [Eventim Scraper: Events & Ticket Prices Germany](https://apify.com/bovi/eventim-scraper) — public event listings and ticket prices in Germany.
- [Songkick Scraper - Concerts, Tour Dates & Tickets](https://apify.com/bovi/songkick-scraper) — public concert, tour-date and ticket data.

# Actor input Schema

## `startUrls` (type: `array`):

EaseMyTrip hotel pages to collect from: a city or category listing (e.g. https://www.easemytrip.com/hotels/hotels-in-goa/), a single hotel page, or a hotel sitemap XML (e.g. https://www.easemytrip.com/sitemap/hotels-desc1.xml).

## `maxResults` (type: `integer`):

Maximum number of hotel records to collect.

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

Optional. Apify Proxy settings. The site is reachable without a proxy from most IPs; turn the proxy on if you get blocked.

## Actor input object example

```json
{
  "startUrls": [
    {
      "url": "https://www.easemytrip.com/hotels/hotels-in-goa/"
    }
  ],
  "maxResults": 50,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ]
  }
}
```

# Actor output Schema

## `results` (type: `string`):

Dataset with the scraped hotel records.

# 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 = {
    "startUrls": [
        {
            "url": "https://www.easemytrip.com/hotels/hotels-in-goa/"
        }
    ],
    "proxyConfiguration": {
        "useApifyProxy": true,
        "apifyProxyGroups": [
            "RESIDENTIAL"
        ]
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("bovi/easemytrip-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 = {
    "startUrls": [{ "url": "https://www.easemytrip.com/hotels/hotels-in-goa/" }],
    "proxyConfiguration": {
        "useApifyProxy": True,
        "apifyProxyGroups": ["RESIDENTIAL"],
    },
}

# Run the Actor and wait for it to finish
run = client.actor("bovi/easemytrip-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 '{
  "startUrls": [
    {
      "url": "https://www.easemytrip.com/hotels/hotels-in-goa/"
    }
  ],
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ]
  }
}' |
apify call bovi/easemytrip-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,bovi/easemytrip-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/DWWxpyxs55wHun6Xg/builds/U8uz9g6I4kQfVmKDu/openapi.json
