Apartments.com Scraper - Rentals, Prices & Property Details avatar

Apartments.com Scraper - Rentals, Prices & Property Details

Pricing

from $1.50 / 1,000 results

Go to Apify Store
Apartments.com Scraper - Rentals, Prices & Property Details

Apartments.com Scraper - Rentals, Prices & Property Details

From $1.50/1K. Scrape Apartments.com rentals by city, ZIP, neighborhood, address or URL. Extract rent, floorplans, available units, amenities, fees, schools, transit, ratings, reviews, photos, phone numbers and GPS coordinates.

Pricing

from $1.50 / 1,000 results

Rating

0.0

(0)

Developer

Abot API

Abot API

Maintained by Community

Actor stats

1

Bookmarked

4

Total users

1

Monthly active users

10 days ago

Last modified

Share

Apartments.com Scraper: Rentals, Floorplans & Contacts

Apartments.com Scraper turns Apartments.com into structured rental data. Search any US city, ZIP, neighborhood or street address, paste result and property links directly, or resolve a search term to a location with autocomplete. Every property comes back as one rich row with rent range, floorplans, available units, amenities, pet and parking policy, fees, nearby schools, walk and transit scores, office hours, ratings, reviews, photos, phone and GPS coordinates. Export to JSON, CSV or Excel, or read results straight through the Apify API.

Why This Scraper?

  • One row per property, not one row per sub-block. Amenities, fees, schools, units and reviews all live inside the same record instead of being split into separate rows you'd otherwise pay for one by one.
  • 50+ fields per property, including floorplan models, every available unit with rent and square footage, the full amenity list, pet and parking policy, fee schedule, nearby schools, walk and transit scores, office hours, ratings and recent reviews.
  • Three modes: location search with filters, direct URL scraping (result pages and property pages, mixed in one run), and location autocomplete for resolving a term to coordinates.
  • Graceful pagination that walks a whole result set on its own, bounded only by a single soft cap (maxListings), with duplicate properties removed automatically.
  • Daily/recurring change monitoring. Turn on Incremental mode to track a search over time and receive only the properties that are new, updated or reappeared on each scheduled run.
  • Resume support for one specific interrupted or previous large crawl via resumeFromRunId, plus an internal checkpoint that survives platform migrations without re-billing already-saved properties.
  • A refused run fails loudly with a clear status message instead of quietly returning an empty dataset that looks like a genuine "no results" search.

Use Cases

  • Rental market research and investors: compare rent ranges, unit mixes and amenities across a metro to spot pricing trends over time.
  • Listing aggregator and search apps: pull structured floorplans, units and availability to power your own rental search tool.
  • Property management competitive intelligence: track competitors' rent specials, fees and policies with Incremental mode so you only see what changed.
  • Relocation and leasing services: collect management company names, phone numbers and office hours tied to specific neighborhoods.
  • Neighborhood and livability research: pair school, walk score and transit data with rent to study a market beyond price alone.

Data You Get

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

FieldExample
idabc1234
nameSample Apartments
urlhttps://www.apartments.com/sample-apartments-austin-tx/abc1234/
descriptionA modern community near downtown with resort-style amenities.
address / city / state / zip100 Example St, Austin, TX 78701 / Austin / TX / 78701
latitude / longitude30.0000 / -97.0000
rentMin / rentMax / currency1200 / 2600 / USD
bedsRange / bathsRange / sqftRange1 - 2 bd / 1 - 2 ba / 500 - 1,000
propertyTyperental (or the plural filter value, e.g. apartments, when one is set)
yearBuilt / unitsInBuilding / stories2010 / 200 / 4
neighborhood / leaseOptionsSample Neighborhood / 6 - 15 Month Leases
managementCompany / rentSpecial / verifiedSample Management Co / Move-in special: one month free / true
phone / petsAllowed(800) 000-0000 / true
rating / reviewCount4.1 / 12
amenities["Pool", "Fitness Center", "In Unit Laundry"]
floorplans[{ "name": "A1", "rent": "$1,200 - $1,400", "beds": 1, "baths": 1, "sqft": 650 }]
units[{ "model": "A1", "unit": "000", "beds": 1, "baths": 1, "rent": 1300, "sqft": 650, "availability": "Now" }]
fees / parking["Application Fee $0"] / ["Garage - $0/mo"]
transit / schools[{ "name": "Sample Station", "distanceMiles": 1.0, "driveTimeMin": 5 }] / [{ "name": "Example Elementary", "type": "Public", "grades": "PK-5", "students": 500 }]
walkScore{ "walk": 80, "transit": 50, "drive": 90, "bike": 70 }
officeHours / reviews["Monday, Tuesday, Wednesday, Thursday, Friday: 09:00-18:00"] / [{ "author": "A. Renter", "rating": 5, "title": "Great place", "body": "Sample review text.", "date": "2026-01-01" }]
photos["https://images1.apartments.com/i2/0000/sample-photo.jpg"]
detailScraped / scrapedAttrue / 2026-01-01T00:00:00.000Z
changeTypeNEW (incremental mode only, see How to Use)

Search-result cards (search mode, and any url-mode entry that resolves to a result page rather than a single property) also carry street, bedsLabel (e.g. "Studio - 2 Beds"), amenitiesSummary (a short card-text summary) and a single photo thumbnail URL; these sit alongside the detail fields above once fetchDetails enriches the record, but a directly pasted single-property URL is scraped straight from its detail page and never carries them. Every detail-scraped record also keeps rawJsonLd, the underlying source object the detail fields were parsed from. Autocomplete-mode rows have a completely different shape: query, id, display, geographyType, city, state, county, latitude, longitude, boundingBox and scrapedAt, with no property fields at all. In Incremental mode, every classified row adds changeType, changedFields (populated only for UPDATED), firstSeenAt and lastSeenAt.

How to Use

  1. Pick a mode: search (location plus filters), url (paste result or property links), or autocomplete (location suggestions only, no listings).
  2. For search mode, fill in locations and any filters; for URL mode, paste your links. Switch Fetch full property details on or off depending on whether you need the enriched fields.
  3. Set Max properties (and optionally Max result pages) to control run size and cost, then click Start.
  4. Download the dataset as JSON, CSV or Excel, or read it through the API.

Search a city, fast cards only:

{
"mode": "search",
"locations": ["Austin, TX"],
"fetchDetails": false,
"maxPages": 3,
"maxListings": 100
}

Search with filters and full details:

{
"mode": "search",
"locations": ["Denver, CO", "80202"],
"propertyType": "apartments",
"bedrooms": "2",
"minRent": 1500,
"maxRent": 2800,
"fetchDetails": true,
"maxPages": 5
}

Scrape URLs (a result page and a property page, mixed):

{
"mode": "url",
"urls": [
"https://www.apartments.com/houston-tx/2-bedrooms/",
"https://www.apartments.com/sample-apartments-austin-tx/abc1234/"
],
"fetchDetails": true,
"maxPages": 2
}

Location autocomplete:

{
"mode": "autocomplete",
"locations": ["Brooklyn", "78701"]
}

Run it from your code

Python:

from apify_client import ApifyClient
client = ApifyClient("<YOUR_APIFY_TOKEN>")
run = client.actor("abotapi/apartments-com-scraper").call(run_input={"mode": "search", "locations": ["Austin, TX"], "maxListings": 50})
for prop in client.dataset(run["defaultDatasetId"]).iterate_items():
print(prop["name"], prop.get("rentMin"), prop.get("rentMax"))

JavaScript:

import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: '<YOUR_APIFY_TOKEN>' });
const run = await client.actor('abotapi/apartments-com-scraper').call({ mode: 'search', locations: ['Austin, TX'], maxListings: 50 });
const { items } = await client.dataset(run.defaultDatasetId).listItems();

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

How maxPages and maxListings shape a run

By default maxPages is 0 (unlimited): a search or URL entry walks every result page (about 40 properties per page) until Apartments.com naturally runs out, an empty page or one that repeats properties already collected, or until maxListings (the run's only soft cap, default 20, set 0 for unlimited) is reached, whichever comes first. Set maxPages to a specific number only when you want an explicit page cap below that natural stop. For a very large walk-all pull spread across multiple runs, use resumeFromRunId in a follow-up run instead of raising the cap on one run: paste the ID of a previous run (or its dataset) and the new run loads the properties already saved there, skips them, and appends only new properties to a fresh dataset.

Resume and recurring updates

Resume (resumeFromRunId) continues one specific interrupted or previous large crawl: paste a run ID or dataset ID and this run skips properties already collected there, appending only the remaining new properties. An internal same-run checkpoint also protects against platform migrations without any input needed, so an interrupted run picks back up without re-saving (and re-billing) properties it already wrote.

Incremental mode (incrementalMode) is for a recurring schedule (for example, daily) against the same search: the actor remembers state itself, keyed on your search, filter and fetchDetails settings (or an explicit stateKey), so you never paste a run ID. The first run returns every property as NEW. Later runs classify each property as NEW, UPDATED (with changedFields listing exactly what changed), or UNCHANGED (suppressed and not returned or billed as a result unless emitUnchanged is on; detail enrichment still applies to it when fetchDetails is on). Turning on emitExpired also marks properties that were present in a previously tracked run but are no longer found as EXPIRED, but only once a run has scanned the tracked search completely: not capped by maxListings, and not a resumeFromRunId run. A partial scan cannot tell "gone" apart from "not reached yet", so it skips expiry detection instead and keeps the previous state as-is. REAPPEARED can only ever be produced for a property that an earlier complete, emitExpired run has already marked EXPIRED; if emitExpired has never been turned on for a given state key, nothing in that state can come back as REAPPEARED, because nothing was ever marked absent in the first place.

Combining resumeFromRunId with Incremental mode on a state key that has no tracked properties yet seeds that baseline from the resume dataset too, so those properties don't look NEW again on the next scheduled run. Combining it with a state key that already has tracked properties instead fails the run immediately, since it isn't clear which baseline should win; remove resumeFromRunId or set a different stateKey to bootstrap a separate campaign.

Send results into your apps (MCP connectors)

Optionally pipe the scraped results 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 record, not the full JSON. Each item 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 items 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
modestringsearchHow to start: search builds result pages from location terms, url scrapes pasted URLs, autocomplete returns location suggestions only, no listings.
locationsarrayno default (prefill: ["Austin, TX"])City, ZIP, neighborhood, or street address terms, one per line. Used by search and autocomplete; ignored in url mode.
propertyTypestringanyLimit to apartments, houses, condos, townhomes, or any for all types.
bedroomsstringanyMinimum bedroom count: any, studio, 1, 2, 3, 4.
minRentinteger(none)Lowest monthly rent in USD. Leave empty for no minimum.
maxRentinteger(none)Highest monthly rent in USD. Leave empty for no maximum.
lifestylestringnoneOptional single lifestyle filter (for example pet-friendly, luxury, furnished); applied only when propertyType is any.
urlsarrayno default (prefill: ["https://www.apartments.com/austin-tx/"])Apartments.com result or property URLs, one per line. Used by url mode; search-mode filters are ignored.
fetchDetailsbooleantrueEnrich each search-result card with its detail page: floorplan units, full amenities, pet and parking policy, fees, schools, transit, walk score, office hours, ratings and reviews. A property URL you paste directly is always fetched and returned in full regardless of this toggle; it only affects search-result cards and the enrichment billing event, see the FAQ.
maxPagesinteger0Safety bound on result pages walked per location or start URL (about 40 properties per page). 0 means unlimited, the walk stops on its own once a page comes back empty or repeats listings already collected.
maxListingsinteger20The sole soft cap on the run, applied across all locations/URLs. 0 means unlimited.
resumeFromRunIdstring(none)Continue one specific interrupted or previous large crawl: paste a run ID or dataset ID and this run skips properties already collected there.
incrementalModebooleanfalseDaily/recurring monitoring of this same search. First run returns everything as NEW; later runs return only NEW/UPDATED by default. See "Resume and recurring updates" above.
stateKeystring(none)Optional name for a monitoring campaign, so its incremental state stays stable or is deliberately shared. Auto-derived from your search/filter settings when left empty.
emitUnchangedbooleanfalseIncremental mode only. Also return properties unchanged since the last run, marked UNCHANGED. Adds and bills extra rows you already have.
emitExpiredbooleanfalseIncremental mode only. Also return properties from a previous run no longer found, marked EXPIRED, once a run has fully scanned the tracked search (not capped, not a resume). Adds and bills extra synthetic rows.
proxyobjectApify ResidentialConnection settings.
mcpConnectorsarray(none)Optionally send a summary of each record to apps you authorized under Integrations. Leave empty to skip; never changes the dataset output.
notionParentPageUrlstring(none)Notion connector only: URL or ID of the Notion page under which item pages are created. Required for Notion export; ignored by other connectors.
maxNotifyListingsinteger50Cap on the number of items written to each connector per run. Does not affect the dataset.

Output Example

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

{
"id": "abc1234",
"url": "https://www.apartments.com/sample-apartments-austin-tx/abc1234/",
"name": "Sample Apartments",
"description": "A modern community near downtown with resort-style amenities and easy highway access.",
"address": "100 Example St",
"street": "100 Example St",
"city": "Austin",
"state": "TX",
"zip": "78701",
"latitude": 30.0,
"longitude": -97.0,
"rentMin": 1200,
"rentMax": 2600,
"currency": "USD",
"bedsLabel": "Studio - 2 Beds",
"bedsRange": "1 - 2 bd",
"bathsRange": "1 - 2 ba",
"sqftRange": "500 - 1,000",
"propertyType": "rental",
"yearBuilt": 2010,
"unitsInBuilding": 200,
"stories": 4,
"neighborhood": "Sample Neighborhood",
"leaseOptions": "6 - 15 Month Leases",
"managementCompany": "Sample Management Co",
"rentSpecial": "Move-in special: one month free",
"verified": true,
"phone": "(800) 000-0000",
"petsAllowed": true,
"rating": 4.1,
"reviewCount": 12,
"amenities": ["Pool", "Fitness Center", "In Unit Laundry"],
"floorplans": [{ "name": "A1", "rent": "$1,200 - $1,400", "beds": 1, "baths": 1, "sqft": 650 }],
"units": [{ "model": "A1", "unit": "000", "beds": 1, "baths": 1, "rent": 1300, "sqft": 650, "availability": "Now" }],
"fees": ["Application Fee $0", "Admin Fee $0"],
"parking": ["Garage - $0/mo"],
"transit": [{ "name": "Sample Station", "distanceMiles": 1.0, "driveTimeMin": 5 }],
"schools": [{ "name": "Example Elementary", "type": "Public", "grades": "PK-5", "students": 500 }],
"walkScore": { "walk": 80, "transit": 50, "drive": 90, "bike": 70 },
"officeHours": ["Monday, Tuesday, Wednesday, Thursday, Friday: 09:00-18:00"],
"reviews": [{ "author": "A. Renter", "rating": 5, "title": "Great place", "body": "Sample review text.", "date": "2026-01-01" }],
"photo": "https://images1.apartments.com/i2/0000/sample-thumb.jpg",
"photos": ["https://images1.apartments.com/i2/0000/sample-photo.jpg"],
"detailScraped": true,
"scrapedAt": "2026-01-01T00:00:00.000Z"
}

Plan Requirement

Residential proxy is the default and most reliable option for Apartments.com: the actor automatically varies the connection across many regions and retries on a fresh connection when one is refused, so runs stay stable at scale. Residential requires an Apify plan that includes it; if yours does not, switch to Datacenter under Connection instead, it still works well when connections are healthy and also retries on a fresh connection when refused. Apartments.com shows the same United States listings regardless of the connecting region, so the regional variety is purely for reliability, not different data. The actor also recovers automatically from a single refused page, so one rejected request does not stop the run.

FAQ

How much does it cost?

You pay per property returned, plus optional detail-page enrichment when fetchDetails is switched on, which also applies to a pasted single property URL. The Pricing tab on this actor's Store page shows the current rates. Use Max properties to cap the cost of any run.

This actor collects only publicly available rental listing data. You are responsible for how you use it: follow Apartments.com's terms and the laws that apply to you, and get legal advice if you plan commercial redistribution. Contact details, photos and reviews on individual listings may be subject to third-party rights.

Can I get only new or changed properties on a schedule?

Yes. Schedule the actor from the Schedules tab and turn on Incremental mode. Each run then returns only new and updated properties for the same search; unchanged properties are not returned or billed as results unless you turn emitUnchanged on, though detail enrichment still applies to them when fetchDetails is on.

Why doesn't turning off fetchDetails change anything for a pasted property URL?

fetchDetails only controls whether search-result cards get a detail-page visit. A URL you paste that already points straight at one property page is always fetched and returned with the full detail fields (floorplans, units, fees, schools, and more); turning fetchDetails off in that case only skips the detail-enrichment billing event for that record, it does not skip the fetch or shrink the returned data.

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

If every request this run made was refused and nothing at all could be read, the run fails with a clear status message instead of quietly returning zero properties, so a genuine block is never confused with an empty search. A run where the site answered but had no matching properties still succeeds, with one row explaining that. Missing required input for the selected mode (for example, search mode with no locations) also fails immediately, before any proxy or browser session is paid for.

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 results into Notion, Linear or Airtable.

🔗 Want more real estate data?

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

🏠 591.com.tw Scraper
Extract property listings from 591房屋交易網 591.com.tw, Taiwan’s largest real estate...
🏠 Rent.com Scraper
Extract rental listings from rent.com. Get comprehensive data including monthly rent...
🏠 Crexi Scraper
Scrape crexi.com commercial listings: asking price, cap rate, square footage, units, year...
🏠 Zumper
Scrape Zumper.com rental listings: apartments, houses, condos and rooms. Pulls 60+ fields...
🏠 OnTheMarket Scraper
Scrape onthemarket.com for-sale, to-rent and new-homes listings with 85+ fields: price...
🏠 StreetEasy Scraper
Scrape StreetEasy sales, rentals and in-contract listings across NYC and Jersey City...

👉 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 contact@abotapi.com or message Telegram @abotapi.
  • ⭐ Enjoying it? A quick review on the actor page helps other users find it.