# Hotels.com API for hotel prices, rate plans and reviews

> Find a hotel’s Hotels.com id by name, then read what a guest on the Hotels.com site for their country sees: the headline price for a stay, every room type and rate plan, and the guest reviews.

Canonical page: https://scrapercompany.com/hotels-com-api. Endpoints and prices checked against the API on 2026-10-11.

Hotels.com is an Expedia Group brand with separate sites for many countries, so a hotel’s price there can differ from Expedia’s and from one Hotels.com site to the next. Teams that watch rate parity or a competitive set track it as its own channel. Hotels.com has no developer API for reading prices, so this API returns the public Hotels.com result as data.

Two things make Hotels.com easy to get wrong. The number in many hotel page URLs is a legacy id that does not price, and the headline price on the US and German sites is the stay total, not a nightly rate. The search endpoint returns the id that does price, and the headline price comes with a label saying whether it is a stay total or a nightly figure. Each call prices one stay of up to 30 nights on the Hotels.com site you choose: the US, UK, Canada, Ireland, Germany, France and others.

## What you get

- `recommended_match.property_id`: the hotel’s numeric Hotels.com id from a name and city search, with a confidence level
- `price_per_night, price_per_night_is`: the headline price, and whether it is the stay total or a nightly figure
- `total, nightly`: the stay total and nightly price, when Hotels.com labels them
- `rooms[].rate_plans[]`: price per rate plan, with total, nightly and taxes_and_fees
- `refundable, cancellation_text`: whether the plan can be cancelled for free, and Hotels.com’s wording
- `payment_model, pay_now`: pay now or pay at the property
- `availability`: available, sold out or a minimum stay
- `reviews[]`: rating out of 10, text, date, length of stay and labels such as Verified review

## Endpoints and price per call

| Endpoint | Method and path | What it returns | Credits per successful call | Price per call |
| --- | --- | --- | --- | --- |
| [Hotel search](https://scrapercompany.com/docs/reference/hotels-search) | `POST /v1/ota/hotels/search` | Hotels.com property id for a hotel name and city, with match confidence | 2 credits | $0.0020 on Starter, $0.0012 on Growth, $0.0008 on Scale |
| [Headline price](https://scrapercompany.com/docs/reference/hotels-price) | `POST /v1/ota/hotels` | The lead price for one stay, with labelled total and nightly figures | 8 credits | $0.0078 on Starter, $0.0048 on Growth, $0.0032 on Scale |
| [Rooms and rate plans](https://scrapercompany.com/docs/reference/hotels-rooms) | `POST /v1/ota/hotels/rooms` | Every room type and rate plan for one stay | 8 credits | $0.0078 on Starter, $0.0048 on Growth, $0.0032 on Scale |
| [Reviews](https://scrapercompany.com/docs/reference/hotels-com-reviews) | `POST /v1/ota/hotels/reviews` | Guest reviews, newest first, up to 25 per page | 2 credits | $0.0020 on Starter, $0.0012 on Growth, $0.0008 on Scale |

Pricing: Free $0/month for 1,000 credits; Starter $49/month for 50,000 credits; Growth $149/month for 250,000 credits; Scale $399/month for 1,000,000 credits. Failed requests (4xx or 5xx) and empty results cost 0 credits. Free during the beta. https://scrapercompany.com/pricing

## Example

`POST /v1/ota/hotels/rooms`, 8 credits per successful call.

```bash
curl -X POST "https://api.scrapercompany.com/v1/ota/hotels/rooms" \
  -H "x-api-key: $SCRAPERCOMPANY_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "property_id": "12570",
    "check_in": "2026-12-10",
    "nights": 1,
    "market": "US"
  }'
```

Response (trimmed):

```json
{
  "property_id": "12570",
  "market": "US",
  "check_in": "2029-04-23",
  "check_out": "2029-04-24",
  "nights": 1,
  "currency": "USD",
  "requested_currency": "USD",
  "currency_verified": true,
  "available": true,
  "sold_out": false,
  "availability": "available",
  "is_soldout": false,
  "cheapest_rate": 475,
  "wire_bytes": 181614,
  "egress_mode": "direct",
  "rooms": [
    {
      "name": "Room, 2 Double Beds",
      "unit_id": "16572",
      "cheapest_rate": 635,
      "rate_plans": [
        {
          "plan_id": "266071193",
          "price": 635,
          "price_text": "$635 total",
          "currency": "USD",
          "refundable": false,
          "refundable_until": "",
          "pay_now": true,
          "provenance": {
            "schema_version": 1,
            "observation_id": "rateobs_0123456789abcdef0123456789abcdef",
            "collection_id": "ratecol_0123456789abcdef0123456789abcdef",
            "observed_at": "2026-08-07T01:23:45.678Z",
            "source": "hotels_com",
            "source_kind": "ota_rate_plan",
            "collector": "scrapingme.ota.hotels_rooms",
            "source_property_id": "12570",
            "requested_market": "US",
            "requested_currency": "USD",
            "returned_currency": "USD",
            "egress_mode": "direct",
            "price_basis": "stay_rate_plan",
            "derivation": "upstream",
            "upstream_rate_id": "266071193"
          },
          "room_type_id": "16572",
          "payment_model": "PAY_NOW",
          "hotel_collect": false,
          "total": 635,
          "nightly": 509,
          "taxes_and_fees": 126,
          "taxes_and_fees_provenance": {
            "schema_version": 1,
            "observation_id": "rateobs_0123456789abcdef0123456789abcdef",
            "collection_id": "ratecol_0123456789abcdef0123456789abcdef",
            "observed_at": "2026-08-07T01:23:45.678Z",
            "source": "hotels_com",
            "source_kind": "ota_rate_plan",
            "collector": "scrapingme.ota.hotels_rooms",
            "source_property_id": "12570",
            "requested_market": "US",
            "requested_currency": "USD",
            "returned_currency": "USD",
            "egress_mode": "direct",
            "price_basis": "taxes_and_fees_combined",
            "derivation": "total_minus_nightly_times_nights",
            "upstream_rate_id": "266071193"
          },
          "total_text": "$635 total",
          "nightly_text": "$509 nightly",
          "taxes_and_fees_included": true,
          "cancellation_text": "Non-Refundable",
          "extras_text": "No extras",
          "member_only": false,
          "inventory_type": "MERCHANT",
          "business_model": "EXPEDIA_COLLECT"
        },
        {
          "plan_id": "266071191",
          "price": 742,
          "price_text": "$742 total",
          "currency": "USD",
          "refundable": true,
          "refundable_until": "Nov 14",
          "pay_now": false,
          "room_type_id": "16572",
          "payment_model": "PAY_LATER",
          "hotel_collect": true,
          "total": 742,
          "nightly": 599,
          "taxes_and_fees": 143,
          "total_text": "$742 total",
          "nightly_text": "$599 nightly",
          "taxes_and_fees_included": true,
          "cancellation_text": "Fully refundable before Nov 14",
          "extras_text": "No extras",
          "member_only": false,
          "inventory_type": "DIRECT_AGENCY",
          "business_model": "HOTEL_COLLECT"
        }
      ]
    },
    {
      "name": "Suite, Multiple Beds, Non Smoking",
      "unit_id": "325392434",
      "rate_plans": []
    }
  ]
}
```

## FAQ

### Does Hotels.com have a public API?

Hotels.com does not publish a developer API of its own. It is an Expedia Group brand, and Expedia Group’s partner APIs are open by application to businesses that sell its inventory or supply rooms. ScraperCompany is independent of Expedia Group: this API reads the prices, rooms and reviews the public Hotels.com sites show.

### How do I find a hotel’s Hotels.com property id?

Send the hotel name and city to the hotel search endpoint and store recommended_match.property_id. In a URL like hotels.com/h38766175.Hotel-Information, the id is 38766175. Many page URLs carry an older number after /ho instead; the price endpoints read that as an unknown hotel and answer that no rooms are available, so use the search endpoint’s id.

### Why is price_per_night sometimes the price of the whole stay?

It is the headline price as Hotels.com shows it, and on the US and German sites that headline is the stay total including taxes and fees. price_per_night_is says whether it is a stay total, a nightly price or unknown. Use total and nightly when you need a figure with a fixed meaning.

### Can I compare Hotels.com prices across countries?

Not directly. Each Hotels.com site sets its own currency and shows prices on its own basis, so converting one site’s price into another currency does not give the other site’s price. Pick one market per comparison.

### Are Hotels.com reviews the same as Expedia’s?

No. Both are Expedia Group brands, but each site keeps its own guest reviews. Use the Hotels.com reviews endpoint for Hotels.com and the Expedia reviews endpoint for Expedia.

### Do failed requests cost credits?

No. A failed or blocked call (any 4xx or 5xx response) costs 0 credits, and so does a search page that comes back empty. You pay only for successful results.

### How do I get an API key?

Create an account on the sign-up page. Public sign-up is invite-only during the beta, so join the waitlist there and we will email you when your account is ready. The Free plan includes 1,000 credits a month, and the API is free while it is in beta. You create and rotate keys yourself in the dashboard.

## Read next

- [Expedia API](https://scrapercompany.com/expedia-api)
- [Compare OTA rates guide](https://scrapercompany.com/docs/guides/compare-ota-rates)
- [Hotel reviews guide](https://scrapercompany.com/docs/guides/hotel-reviews)
- [All APIs](https://scrapercompany.com/apis.md)
