Airbnb Listings Scraper
Pricing
from $2.98 / 1,000 results
Airbnb Listings Scraper
Scrape Airbnb listings and return structured data including listing names, nightly rates, stay totals, ratings, bedroom and bathroom details, badges, coordinates and photos. Add guest and date filters, search locations or map areas, and optionally retrieve public host details from listing pages.
Pricing
from $2.98 / 1,000 results
Rating
0.0
(0)
Developer
Axiom Works
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
8 days ago
Last modified
Categories
Share
Returns: one row per Airbnb listing with name, title, pricePerNight, totalPrice, rating, reviewCount, bedrooms, hostName, latitude, longitude and photos.
Input: {"locations": ["Lisbon, Portugal"], "adults": 2, "maxItems": 50}
Best for: short-term rental market research, competitor price monitoring, travel and investment lead lists.
{"id": "32422325","sourceUrl": "https://www.airbnb.com/rooms/32422325","name": "Brand new apartment right in the heart of Alfama.","title": "Apartment in Santa Maria Maior","pricePerNight": 124.95,"rating": 4.82,"reviewCount": 478,"hostName": "BB Lisbon"}
What does Airbnb Listings Scraper do?
Airbnb Listings Scraper is an Airbnb scraper and unofficial Airbnb API for search results. You give it one or more places (for example "Lisbon, Portugal" or "Austin, TX"), optional check-in and check-out dates, the number of guests and a price range. It returns the listings Airbnb shows for that search as clean, structured rows that you can export to JSON, CSV, Excel or HTML, or read through the Apify API.
For every listing you get the host's listing name, the card title (property type and area), the nightly rate, the stay total, any strikethrough original price, the average rating and review count, bedrooms, beds and bathrooms, the host type, coordinates and a list of photo URLs. With host details switched on, the scraper also opens each listing page to add the public host name, host id, Superhost and verified flags, guest capacity, room type and the six rating sub-scores.
You can search by place name, paste full Airbnb search URLs (including map-area URLs with bounding-box coordinates), or paste a single listing URL. The scraper works without an Airbnb account and without logging in. It only reads public pages that anyone can open in a browser.
This tool is an independent project. It is not affiliated with, endorsed by or connected to Airbnb.
What data can you get?
Each dataset row describes one listing. Fields that Airbnb does not show for a listing are returned as null.
| Field | Type | Description |
|---|---|---|
id | string | Airbnb numeric listing id, unique within a run |
sourceUrl | string | Link to the listing page |
name | string | Listing name chosen by the host |
title | string | Card title, property type and area |
pricePerNight | number | Nightly rate in the chosen currency |
totalPrice | number | Stay total for the nights shown |
originalTotalPrice | number | Total before discount, when Airbnb shows a strikethrough price |
nights | integer | Number of nights the price is quoted for |
currency | string | Currency code of all prices |
priceLabel | string | Raw price text from the card |
rating | number | Average guest rating out of 5 |
reviewCount | integer | Number of guest reviews |
bedrooms | integer | Bedrooms, 0 for studios |
beds | integer | Number of beds |
bathrooms | number | Bathrooms, 0.5 for a half bath |
bathroomLabel | string | Raw bathroom text |
hostType | string | Business host or Individual host |
hostName | string | Public host name (host details on) |
hostId | string | Airbnb host id (host details on) |
hostIsSuperhost | boolean | Superhost flag (host details on) |
hostIsVerified | boolean | Verified host flag (host details on) |
hostPhoto | string | Host profile picture URL (host details on) |
personCapacity | integer | Maximum guests (host details on) |
roomType | string | Room type such as Entire home/apt (host details on) |
description | string | Full listing description as plain text (host details on) |
amenities | array | Amenities the listing offers, such as Wifi or Kitchen (host details on) |
checkInTime | string | House-rule check-in window (host details on) |
checkOutTime | string | House-rule check-out time (host details on) |
subRatings | object | Accuracy, checkin, cleanliness, communication, location and value scores (host details on) |
badges | array | Card badges such as Guest favorite |
latitude | number | Approximate latitude of the listing pin |
longitude | number | Approximate longitude of the listing pin |
photos | array | Up to 8 listing photo URLs |
thumbnail | string | First photo URL |
searchLocation | string | The location or URL that produced the row |
position | integer | Rank of the listing within its search |
checkIn | string | Requested check-in date, null when Airbnb default dates were used |
checkOut | string | Requested check-out date, null when Airbnb default dates were used |
scrapedAt | string | ISO timestamp of extraction |
Some notes on how the values behave:
- Prices depend on the dates, currency and number of guests you choose. When you give no dates, Airbnb quotes its own default stay, and
nightstells you how many nights that is. pricePerNightis the nightly rate Airbnb shows in the price breakdown. Taxes and fees are part oftotalPricewhere Airbnb includes them.- Coordinates are the obfuscated pin Airbnb publishes, accurate to roughly a hundred metres, not an exact address.
- Hotels and some room types have no bedroom line on the card, so
bedroomscan be null. - New listings without reviews have a null
rating.
How to use
- Open the Actor in Apify Console and go to the Input tab.
- Enter one or more places in Locations, for example
Lisbon, Portugal. You can add several; results are merged and de-duplicated by listing id. - Optionally set check-in and check-out dates, adults, children, infants and pets. Dates must be in the future and use the format YYYY-MM-DD.
- Optionally set a minimum and maximum nightly price and a currency.
- Choose Max listings. The limit counts all locations together.
- Leave Include host details on if you need host names and sub-ratings. Switch it off for a faster run that makes one request per page of 18 listings instead of one per listing.
- Click Start. Results appear in the Output tab while the run is going.
Airbnb returns at most 270 listings per search (15 result pages of 18). For a large city, split the search into neighbourhoods ("Alfama, Lisbon") or use map-area URLs from the Airbnb website to cover the city in pieces. Each piece can return its own 270 listings.
If the place name is not recognised, Airbnb would normally show unrelated listings from around the world. The scraper detects this, skips that location, logs a warning and returns nothing for it, instead of filling your dataset with the wrong places. The run still ends successfully and the status message names the location that was not found.
Input
| Field | Type | Description |
|---|---|---|
locations | array of strings | Places to search, for example Lisbon, Portugal |
startUrls | array | Airbnb search URLs or single listing URLs |
checkIn | string | Check-in date, YYYY-MM-DD |
checkOut | string | Check-out date, YYYY-MM-DD, after check-in |
adults | integer | Adults, 1-16, default 2 |
children | integer | Children, 0-16, default 0 |
infants | integer | Infants, 0-5, default 0 |
pets | integer | Pets, 0-5, default 0 |
minPrice | integer | Minimum nightly price in the chosen currency |
maxPrice | integer | Maximum nightly price in the chosen currency |
currency | string | USD, EUR, GBP, CAD, AUD, JPY, CHF, MXN, BRL or INR |
maxItems | integer | Maximum listings in total, 1-1000, default 50 |
includeHostDetails | boolean | Open each listing page for host fields, default true |
proxyConfiguration | object | Apify Proxy settings |
Example input:
{"locations": ["Lisbon, Portugal", "Porto, Portugal"],"checkIn": "2027-03-12","checkOut": "2027-03-15","adults": 2,"currency": "EUR","minPrice": 50,"maxPrice": 300,"maxItems": 100,"includeHostDetails": true,"proxyConfiguration": { "useApifyProxy": true }}
You can also pass full URLs:
{"startUrls": [{ "url": "https://www.airbnb.com/s/Barcelona--Spain/homes?adults=2" },{ "url": "https://www.airbnb.com/rooms/32422325" }],"maxItems": 25}
Search URLs keep the filters already in the link, and the Actor fills in anything missing from your input. A listing URL returns that one listing; its price fields are null because a listing page alone carries no quote for a stay.
Output
Results are stored in the default dataset. The Overview view shows photo, name, title, price per night, currency, rating, reviews, bedrooms, beds, bathrooms, host name, host type, coordinates and link. A real record from a test run:
{"id": "32422325","sourceUrl": "https://www.airbnb.com/rooms/32422325","name": "Brand new apartment right in the heart of Alfama.","title": "Apartment in Santa Maria Maior","pricePerNight": 124.95,"totalPrice": 401.88,"originalTotalPrice": 470,"nights": 3,"currency": "USD","rating": 4.82,"reviewCount": 478,"bedrooms": 1,"beds": 2,"bathrooms": 1,"bathroomLabel": "1 bath","hostType": "Business host","badges": [],"hostName": "BB Lisbon","hostIsVerified": true,"personCapacity": 4,"roomType": "Entire home/apt","description": "<full plain-text description of the listing>","amenities": ["Wifi", "Kitchen", "Air conditioning"],"checkInTime": "Check-in after 3:00 PM","checkOutTime": "Checkout before 12:00 PM","subRatings": {"accuracy": 4.75,"checkin": 4.73,"cleanliness": 4.69,"communication": 4.71,"location": 4.62,"value": 4.46},"latitude": 38.71167,"longitude": -9.12559,"thumbnail": "https://a0.muscache.com/im/pictures/7410b1e6-ec06-45c6-87ff-2346cea9fe5f.jpg","searchLocation": "Lisbon, Portugal","position": 2,"checkIn": null,"checkOut": null,"scrapedAt": "2026-10-03T12:00:00.000Z"}
Every run also writes a RUN_SUMMARY record to the key-value store with the number of listings, the locations that were not recognised and the final status message.
How much does it cost?
You are charged per result, which means per listing pushed to the dataset. The unit price is shown on the Pricing tab of this Actor, and Apify platform usage such as compute and proxy traffic is billed according to your plan. The number of results is capped by maxItems, so you can always limit what a run can spend by setting a lower value. Turning host details off reduces run time and platform usage.
Use with AI agents (MCP)
You can call this Actor from any MCP-compatible assistant through the Apify MCP server. Add this to your client configuration:
{"mcpServers": {"apify": {"url": "https://mcp.apify.com?tools=axiomworks/airbnb-listings-scraper"}}}
Example prompts:
- "Find 30 Airbnb listings in Lisbon for two adults and list name, price per night and rating."
- "Scrape Airbnb stays in Austin, TX from 2027-03-12 to 2027-03-15 for four guests and show the five best rated."
- "Compare the nightly price of Airbnb homes in Tulum and Hallstatt between 50 and 400."
The input field descriptions are written so that an agent can fill them in without further help.
Integrations and API
Run the Actor from code with the Apify client libraries or the REST API.
Python
from apify_client import ApifyClientclient = ApifyClient("<YOUR_APIFY_TOKEN>")run = client.actor("axiomworks/airbnb-listings-scraper").call(run_input={"locations": ["Lisbon, Portugal"],"adults": 2,"maxItems": 50,})for item in client.dataset(run["defaultDatasetId"]).iterate_items():print(item["name"], item["pricePerNight"], item["currency"])
JavaScript
import { ApifyClient } from 'apify-client';const client = new ApifyClient({ token: '<YOUR_APIFY_TOKEN>' });const run = await client.actor('axiomworks/airbnb-listings-scraper').call({locations: ['Lisbon, Portugal'],adults: 2,maxItems: 50,});const { items } = await client.dataset(run.defaultDatasetId).listItems();console.log(items.length);
cURL
curl -X POST "https://api.apify.com/v2/acts/axiomworks~airbnb-listings-scraper/run-sync-get-dataset-items" \-H "Authorization: Bearer $APIFY_TOKEN" \-H "Content-Type: application/json" \-d '{"locations": ["Lisbon, Portugal"], "adults": 2, "maxItems": 20}'
You can also connect the dataset to Google Sheets, Make, Zapier, n8n or a webhook, and schedule runs to track prices over time.
FAQ
How many listings can I get per search? Airbnb shows up to 270 listings per search. To go beyond that, run several narrower searches, such as neighbourhoods or map-area URLs.
Why is bedrooms or hostType sometimes null?
Airbnb's search cards show only some of these lines for a given search. The Actor fills gaps from the listing page when host details are on, but hotels and some rooms simply have no bedroom count.
Why do I get different prices than on the website? Airbnb prices depend on dates, guests, currency and the visitor's region. Set the same dates, guests and currency in the input to get comparable numbers. Without dates Airbnb quotes its own default stay.
What happens with past dates? They are dropped with a warning and Airbnb's default stay is used, so the run does not fail.
Do I need an Airbnb account? No. The Actor reads public pages only and never logs in.
What if Airbnb blocks requests? Requests that are blocked are retried a few times on a fresh proxy session with a pause. If the datacenter proxy is not enough, switch the proxy setting to residential.
Can I scrape a single listing?
Yes. Put the listing URL in startUrls. You get that listing's name, title, rating, bedrooms, host and sub-rating fields.
Does it return reviews or calendars? No. This Actor returns search-result listings. Availability calendars are a separate tool.
Is it legal to scrape Airbnb?
The Actor collects data that is publicly visible without logging in. Host names are public profile names shown on listing pages. Laws differ by country and by what you do with the data. Personal data, such as a host's name, falls under privacy law like the GDPR in many places, so keep only what you need and have a lawful reason to use it. Airbnb's terms of service restrict automated access, and you are responsible for using the data in line with the rules that apply to you. This is general information, not legal advice; ask a lawyer if you are unsure.
Feedback
If a field is missing, a search returns something unexpected, or you need an extra field, open an issue from the Actor page in Apify Console. Include the input you used and the run link so the problem can be reproduced.