# Property Finder Scraper - UAE Real Estate Listings (Dubai) (`rjmacarthy/propertyfinder-scraper`) Actor

Scrape Property Finder (propertyfinder.ae, also .qa, .eg, .bh) sale and rent listings: price, AED/sqft, beds, size, off-plan vs ready, location, amenities, photos, broker agency, DLD permit link (details). Search by city/community or paste URLs. Price-change monitor. No agent personal data.

- **URL**: https://apify.com/rjmacarthy/propertyfinder-scraper.md
- **Developed by:** [rj](https://apify.com/rjmacarthy) (community)
- **Categories:** Real estate, E-commerce, Automation
- **Features:** Limited permissions
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.00 / 1,000 property listing scrapeds

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

## Property Finder Scraper - UAE Real Estate Listings (Dubai, Abu Dhabi)

Scrape property listings for sale and rent from **Property Finder** (propertyfinder.ae), the UAE's largest property portal, plus its Qatar, Egypt and Bahrain sites. Pick a **purpose, city, community and property type** (for example "2-bedroom apartments for rent in Dubai Marina"), or paste any Property Finder page URL. Each listing comes back as clean JSON with numeric price and **price per sqft**, bedrooms, bathrooms, size, **off-plan vs ready**, furnishing, community / building and coordinates, amenities, photos, and the listing's **broker (agency)**. With `fetchDetails` you also get the **DLD permit validation link**, the brokerage licence number, service charges and recorded transactions of similar units. Turn on **trackPriceChanges** and schedule a daily run to get price changes, or **onlyNew** to get only new listings. You don't need to copy URLs by hand, there's no start fee and no login, and the Actor never outputs agents' personal data.

### What data can you get?

| Field | Example | Notes |
|---|---|---|
| `id`, `url`, `title`, `reference` | 132491576, listing link, "Large Layout | Marina Views", YHUPr-S-126498 | |
| `propertyType`, `purpose`, `category` | Apartment, sale, residential | rent / sale; residential / commercial |
| `price`, `currency`, `pricePeriod` | 2650000, AED, sell | rentals: `yearly` / `monthly` / `weekly` / `daily`; null when the price is hidden |
| `pricePerSqft` | 1530 | as shown by Property Finder (converted from sqm on .eg) |
| `bedrooms`, `bathrooms` | 2, 2 | 0 = studio |
| `size`, `sizeUnit`, `sizeSqft` | 1732, sqft, 1732 | |
| `furnished` | unfurnished | furnished / unfurnished / partly-furnished |
| `completionStatus` | ready | **ready** or **off-plan** (sale listings; usually null for rentals) |
| `locationName`, `city`, `community`, `subCommunity`, `building` | Dubai, Dubai Marina, -, Azure | from Property Finder's location tree |
| `latitude`, `longitude` | 25.0726, 55.1371 | |
| `description` | full listing text | phone numbers and e-mails are removed |
| `amenities`, `images`, `imageCount` | \["Balcony", "Shared Pool"], photo URLs, 19 | 3-5 photos from search results; all, full size, with `fetchDetails` |
| `listedAt`, `updatedAt` | 2026-08-19T08:26:07Z | `updatedAt` only when Property Finder shows a refresh date (rare) |
| `isVerified`, `isPremium`, `isFeatured`, `isExclusive`, `isPriceDrop`, `isDirectFromDeveloper`, `listingLevel` | true, false, ... | Property Finder badges |
| `brokerName`, `brokerId`, `brokerUrl` | YHU Properties | the **agency** only, never the individual agent |
| `permitValidationUrl`, `permitNumber`, `brokerLicenseNumber`, `serviceChargePerSqft`, `availableFrom`, `similarTransactions` | trakheesi.dubailand.gov.ae link, null, 44204, 17.84, 2026-08-19, \[{type: sale, date, price, sizeSqft}] | **with `fetchDetails`**: DLD / regulator advert-permit link (number when the broker publishes it), brokerage licence, service charge, availability date, recorded transactions of similar units in the building. Null without `fetchDetails` |
| `priceChanged`, `previousPrice` | true, 2800000 | with `trackPriceChanges` / `onlyNew` |
| `searchUrl`, `scrapedAt` | | |

### Use cases

- **Investors and analysts:** compare asking price per sqft by community or building, off-plan vs ready, and (with `fetchDetails`) recorded transactions of similar units.
- **Agencies and brokers:** monitor competitor listings and price drops in your communities every day.
- **Relocation and tenants:** collect every furnished 1-bedroom rental in JVC or Dubai Marina under your budget in one spreadsheet.
- **Proptech and data teams:** feed listings into valuation models, dashboards and alerts through the API.

### How to use it

**Fields (no URL copying):** 2-bedroom apartments for rent in Dubai Marina.

```json
{
    "purpose": "rent",
    "city": "dubai",
    "community": "dubai-marina",
    "propertyType": "apartments",
    "minBedrooms": 2,
    "maxBedrooms": 2,
    "maxItems": 100
}
```

- `purpose`: buy, rent, commercial-buy, commercial-rent.
- `city`: "dubai", "abu-dhabi", "sharjah", "ajman", "ras-al-khaimah"... Leave it empty for the whole country.
- `community`: as in Property Finder URLs, e.g. "dubai-marina", "downtown-dubai", "jumeirah-village-circle", "palm-jumeirah", "business-bay", "arabian-ranches".
- `propertyType`: properties (all), apartments, villas, townhouses, penthouses, duplexes, hotel apartments, land, whole buildings, offices, shops, warehouses.
- `country`: ae (default), qa, eg, bh.

**URLs:** open Property Finder, choose Buy or Rent, a location and a property type, and paste the address. You can mix several URLs and countries:

```json
{
    "startUrls": [
        { "url": "https://www.propertyfinder.ae/en/buy/dubai/villas-for-sale-palm-jumeirah.html" },
        { "url": "https://www.propertyfinder.ae/en/rent/abu-dhabi/villas-for-rent.html" }
    ],
    "maxPrice": 60000000,
    "fetchDetails": true,
    "maxItems": 50
}
```

**Daily price monitor:** schedule this every day. The first run saves a baseline. After that, each run outputs only new listings and listings whose price changed, with `priceChanged` and `previousPrice`.

```json
{
    "purpose": "rent",
    "city": "dubai",
    "community": "arabian-ranches",
    "propertyType": "townhouses",
    "onlyNew": true,
    "trackPriceChanges": true,
    "maxPages": 0,
    "maxItems": 0,
    "stateKey": "arabian-ranches-townhouses"
}
```

### Filters are applied after fetching (robots.txt)

Property Finder's robots.txt allows its location and property-type pages and a plain `?page=N`. It disallows its search page and every filter parameter (`price=`, `bedrooms=`, `furnished=`, `ob=` sorting ...). This Actor follows those rules:

- It only requests pages like `/en/rent/dubai/apartments-for-rent-dubai-marina.html?page=2`.
- `minPrice`, `maxPrice`, `minBedrooms`, `maxBedrooms` and `furnished` are applied **locally** to the listings it reads. `maxItems` counts listings *after* filtering, so a narrow filter can read more pages than `maxItems / 25`. `maxPages` caps that.
- If a pasted URL has query parameters (`?price=...&bedrooms=2`), they are removed and a warning is logged. Use the filter fields instead.

### Output example

Real output from a local run (description, photos, amenities and transactions shortened):

```json
{
  "id": "165026014",
  "url": "https://www.propertyfinder.ae/en/plp/buy/villa-for-sale-dubai-palm-jumeirah-garden-homes-garden-homes-frond-f-165026014.html",
  "title": "Incredible Fit Out | Sunset View | Cinema",
  "propertyType": "Villa",
  "purpose": "sale",
  "category": "residential",
  "price": 48950000,
  "currency": "AED",
  "pricePeriod": "sell",
  "pricePerSqft": 6656,
  "bedrooms": 4,
  "bathrooms": 6,
  "size": 7354,
  "sizeUnit": "sqft",
  "sizeSqft": 7354,
  "furnished": "furnished",
  "completionStatus": "ready",
  "locationName": "Garden Homes Frond F, Garden Homes, Palm Jumeirah, Dubai",
  "city": "Dubai",
  "community": "Palm Jumeirah",
  "subCommunity": "Garden Homes Frond F",
  "building": null,
  "latitude": 25.127580642700195,
  "longitude": 55.130062103271484,
  "description": "This newly renovated beachfront villa on Palm Jumeirah defines ultra-luxury island living, combining cutting-edge design with rare lifestyle features. Positioned directly on the shoreline, it offers uninterrupted sunset views and panoramic vistas of Atlantis The Royal and Atlantis The Palm. The resi...",
  "amenities": [
    "Central A/C",
    "Maids Room",
    "Balcony",
    "Covered Parking",
    "View of Water",
    "View of Landmark"
  ],
  "images": [
    "https://static.shared.propertyfinder.ae/media/images/listing/VWBYB14SHHY8RE7MGHH9EDSPNM/6d65ccaa-ecd3-49d3-9252-f42ca81d7401/1312x894.jpg?v=e90612c1ad00934f1bfaa512f7d8d692",
    "https://static.shared.propertyfinder.ae/media/images/listing/VWBYB14SHHY8RE7MGHH9EDSPNM/d2964eeb-cced-4fbd-86ba-0b8a2a159f20/1312x894.jpg?v=1981384232c1305e4e4709ec0fb43740"
  ],
  "imageCount": 30,
  "listedAt": "2026-10-27T06:22:00Z",
  "updatedAt": null,
  "isVerified": true,
  "isPremium": true,
  "isFeatured": false,
  "isExclusive": false,
  "isPriceDrop": false,
  "isDirectFromDeveloper": false,
  "listingLevel": "premium",
  "reference": "RL-251748",
  "permitNumber": null,
  "permitValidationUrl": "https://trakheesi.dubailand.gov.ae/rev/madmoun/listing/validation?khevJujtDig=ui6d4zbmxbdu6omrh7wb4bqfcqhuc9uqjsfswvmhycworamde",
  "brokerLicenseNumber": "25663",
  "brokerId": "4246",
  "brokerName": "White & Co Real Estate",
  "brokerUrl": "https://www.propertyfinder.ae/en/broker/white-co-real-estate-4372-4246",
  "serviceChargePerSqft": null,
  "availableFrom": "2026-05-18T00:00:00Z",
  "similarTransactions": [
    {
      "type": "sale",
      "date": "2026-07-08T00:00:00Z",
      "price": 56000000,
      "sizeSqft": 7058
    },
    {
      "type": "sale",
      "date": "2025-02-24T00:00:00Z",
      "price": 28600000,
      "sizeSqft": 6701
    }
  ],
  "detailsFetched": true,
  "priceChanged": null,
  "previousPrice": null,
  "searchUrl": "https://www.propertyfinder.ae/en/buy/dubai/villas-for-sale-palm-jumeirah.html",
  "scrapedAt": "2026-11-07T12:27:11.752Z"
}
```

### How much does it cost?

Pay per event, no start fee:

| Event | Price | When |
|---|---|---|
| `listing` | **$0.001** | each listing saved to the dataset |
| `listing-details` | **$0.001** | each listing whose page was opened (`fetchDetails: true`) |

Examples:

- 1,000 listings from search results ≈ **$1.00**.
- 1,000 listings with `fetchDetails` ≈ **$2.00**.
- A daily monitor that finds 20 new or re-priced listings costs ≈ **$0.02** per run. Unchanged listings are not charged.

The Actor stops cleanly when it reaches your **Maximum cost per run**.

### Tips and limits

- **Order:** results come in Property Finder's default "Featured" order. Sorting by newest needs a parameter that robots.txt disallows.
- **Monitors:** that "Featured" order rotates. For reliable "only new" alerts, use a narrow search (community + property type) with `maxPages: 0` so the whole search is read. If `maxPages` stops before the end of a monitored search, the run logs a warning.
- **Pages:** about 25 listings per page. `maxPages` defaults to 10 (about 250 listings read per search). 0 means all pages.
- **New-project cards:** developer ads for off-plan projects, mixed into the results, are skipped. Off-plan *listings* are kept and marked `completionStatus: "off-plan"`.
- **Permits:** search results carry no permit data, so the permit fields need `fetchDetails`. Listing pages show the DLD advert permit as a Trakheesi validation link: `permitValidationUrl` is filled and `permitNumber` is usually null.
- **Slugs:** city and community use Property Finder's URL spelling. An unknown slug gives a clear "page not found" error. If in doubt, open the page on the site and paste its URL.
- **Countries:** UAE, Qatar, Egypt and Bahrain were tested. propertyfinder.sa URLs are accepted, but city slugs there differ and were not verified.

### FAQ

**Is it legal to scrape Property Finder?**
This Actor reads only public listing pages that anyone can open without logging in, and it follows the site's robots.txt (no search or filter URLs). It does not collect personal data: no agent names, photos, phone or WhatsApp numbers, e-mails or personal licence numbers. Only the agency (broker company) is output, and phone numbers and e-mails are removed from descriptions. You are responsible for using the data in line with Property Finder's terms, the UAE PDPL, GDPR and other laws that apply to you.

**Can I get the agent's phone number?**
No. That is personal data and is left out on purpose. Use `brokerUrl` to reach the agency through Property Finder.

**Do I need a proxy?**
Usually not. Property Finder served all test requests without one. If a run gets HTTP 403/429, enable Apify Proxy (automatic / datacenter). Residential proxies are not supported: if you select them, the Actor switches to datacenter proxy.

**Why did my filter return fewer listings than `maxItems`?**
Filters run after fetching and `maxPages` limits how many pages are read. Raise `maxPages` (or set it to 0), or use a narrower page, e.g. the community + property type URL.

**What does `fetchDetails` add?**
It opens each listing page for all full-size photos, the DLD permit validation link, the brokerage licence number, the service charge per sqft, the availability date and recorded transactions of similar units in the same building. It costs one extra request and one `listing-details` event per listing.

### Integrations

- **Apify API:** start runs and download datasets from any language ([API docs](https://docs.apify.com/api/v2)), or use the JavaScript and Python clients.
- **Make, Zapier, n8n:** run the Actor on a schedule and send new listings or price changes to Google Sheets, Airtable, Slack, Telegram or e-mail.
- **Webhooks:** call your own endpoint when a run finishes.
- **MCP / AI agents:** call the Actor from Claude, ChatGPT or any MCP client through the Apify MCP server, e.g. "list 3-bedroom villas for rent in Arabian Ranches under AED 300,000 a year".

### Changelog

- **0.1 (November 2026):** first release. Purpose / city / community / type fields or page URLs, UAE + Qatar + Egypt + Bahrain, local price / bedroom / furnishing filters that respect robots.txt, listing pages with transactions and licence, onlyNew and price-change monitor.

### Ready-to-run examples

- [Find 2-bedroom apartments for rent in Dubai Marina](https://apify.com/rjmacarthy/propertyfinder-scraper/examples/2-bedroom-apartments-rent-dubai-marina)

### More scrapers by the same developer

- [AliExpress Scraper - Product Search, Prices, Ratings & Details](https://apify.com/rjmacarthy/aliexpress-scraper)
- [AutoScout24 Scraper - Used Car Listings & Prices (Europe)](https://apify.com/rjmacarthy/autoscout24-scraper)
- [Flipkart Scraper - Prices, Ratings & Offers from Search](https://apify.com/rjmacarthy/flipkart-scraper)
- [Kleinanzeigen Scraper - Germany Classifieds Listings & Prices](https://apify.com/rjmacarthy/kleinanzeigen-scraper)
- [Vinted Scraper: Listings, Prices & New-Item Monitor](https://apify.com/rjmacarthy/vinted-scraper)
- [Apple App Store Scraper: Apps, Search & Reviews](https://apify.com/rjmacarthy/app-store-scraper)

Browse all my Actors on [my Apify Store profile](https://apify.com/rjmacarthy).

### Support

Found a bug or need a field that Property Finder shows? Open an issue on the Actor's **Issues** tab and include your input. Feature requests are welcome.

# Actor input Schema

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

Listing pages from Property Finder, e.g. https://www.propertyfinder.ae/en/buy/dubai/apartments-for-sale-dubai-marina.html or .../en/rent/abu-dhabi/villas-for-rent.html (also propertyfinder.qa, .eg, .bh). Pick a location and property type on the site and copy the address. Query parameters such as ?price= or ?bedrooms= are removed because Property Finder's robots.txt disallows them - use the filters below instead. When URLs are given, the purpose / city / community / type fields are ignored.

## `purpose` (type: `string`):

Used when no URLs are given.

## `country` (type: `string`):

Property Finder site to search when no URLs are given.

## `city` (type: `string`):

As in Property Finder URLs: "dubai", "abu-dhabi", "sharjah", "ajman", "ras-al-khaimah" (Qatar: "doha", "lusail"; Egypt: "cairo"). Leave empty for the whole country.

## `community` (type: `string`):

Optional, as in Property Finder URLs: "dubai-marina", "downtown-dubai", "jumeirah-village-circle", "palm-jumeirah", "business-bay", "yas-island". Spaces are turned into dashes.

## `propertyType` (type: `string`):

Used when no URLs are given.

## `minPrice` (type: `integer`):

Optional. In the site currency (AED on .ae). For rentals this is the advertised rent (usually yearly in the UAE). Applied locally after fetching, because robots.txt disallows the site's filter parameters.

## `maxPrice` (type: `integer`):

Optional. Applied locally after fetching.

## `minBedrooms` (type: `integer`):

Optional. 0 = studio. Applied locally after fetching.

## `maxBedrooms` (type: `integer`):

Optional. Applied locally after fetching.

## `furnished` (type: `string`):

Applied locally after fetching.

## `maxItems` (type: `integer`):

Maximum listings to output per search (after filters). 0 = no limit.

## `maxPages` (type: `integer`):

Each results page has about 25 listings. Results come in Property Finder's "Featured" order (sorting is disallowed by robots.txt), so a monitor must read pages to find new listings. 0 = all pages.

## `fetchDetails` (type: `boolean`):

Also open each listing page for all full-size photos, broker licence number, service charge per sqft, availability date and recent recorded transactions of similar units in the building. One extra request and one "listing-details" event per listing.

## `onlyNew` (type: `boolean`):

Monitor mode: remembers listings between runs (per "Monitor name") and outputs only listings not seen before. The first run outputs everything as the baseline. Schedule the run daily.

## `trackPriceChanges` (type: `boolean`):

Remembers each listing's price between runs and sets priceChanged / previousPrice. Together with "Only new listings", re-priced listings are output too.

## `stateKey` (type: `string`):

Separate monitors (e.g. one per schedule) use different names so their memory is kept apart.

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

Usually not needed. If Property Finder blocks the run (HTTP 403/429), enable Apify Proxy (automatic / datacenter). Residential proxies are not supported: if selected, the run falls back to the datacenter proxy.

## Actor input object example

```json
{
  "startUrls": [
    {
      "url": "https://www.propertyfinder.ae/en/buy/dubai/properties-for-sale.html"
    }
  ],
  "purpose": "buy",
  "country": "ae",
  "city": "dubai",
  "propertyType": "properties",
  "furnished": "any",
  "maxItems": 15,
  "maxPages": 10,
  "fetchDetails": false,
  "onlyNew": false,
  "trackPriceChanges": false,
  "stateKey": "default",
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}
```

# Actor output Schema

## `listings` (type: `string`):

Price, size, location and broker per listing.

## `listingsFull` (type: `string`):

Every field, including description, amenities, photos, permit and price-change data.

## `summary` (type: `string`):

Per-search status, counts, request statistics and warnings.

# 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.propertyfinder.ae/en/buy/dubai/properties-for-sale.html"
        }
    ],
    "maxItems": 15,
    "proxyConfiguration": {
        "useApifyProxy": false
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("rjmacarthy/propertyfinder-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.propertyfinder.ae/en/buy/dubai/properties-for-sale.html" }],
    "maxItems": 15,
    "proxyConfiguration": { "useApifyProxy": False },
}

# Run the Actor and wait for it to finish
run = client.actor("rjmacarthy/propertyfinder-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.propertyfinder.ae/en/buy/dubai/properties-for-sale.html"
    }
  ],
  "maxItems": 15,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}' |
apify call rjmacarthy/propertyfinder-scraper --silent --output-dataset

```

## MCP server setup

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