Domain.com.au API: Australian Listings and Suburb Data
To get Domain.com.au data as JSON, send a GET to https://api.perceptlayer.com/v1/domain-com-au/search with a mode (buy, rent, sold and others) and a suburb. Each call costs 1 credit and returns listings with address, price text, bedrooms, bathrooms, car spaces and agency. The same API also has property detail, auction results by city and suburb insights. This guide covers all four, and when to call realestate.com.au instead.
What can you get from the Domain.com.au API?
The Domain.com.au API has 8 endpoints, all GET, all 1 credit per successful call. Four of them are the ones most projects start with: search, property, auction results and suburb insights. The other four cover people and place lookup: agency, agent, agents and locations.
| Endpoint | Returns | Required parameters |
|---|---|---|
/v1/domain-com-au/search |
Listings for a mode and area | mode |
/v1/domain-com-au/property |
One property | none (listing_id or slug) |
/v1/domain-com-au/auction-results |
Auction results | city |
/v1/domain-com-au/suburb-insights |
Suburb insights | bedrooms, property_type |
/v1/domain-com-au/locations |
Location lookup | q |
/v1/domain-com-au/agents |
Agents, optionally by suburb | none |
/v1/domain-com-au/agent |
One agent | slug |
/v1/domain-com-au/agency |
One agency | slug |
You authenticate with the X-API-Key header. If you don't have a key yet, get a free API key; the authentication docs cover the header and the api_key query fallback.
How do you search Australian listings?
Call search with mode set to one of buy, rent, sold, new-homes, commercial or rural, plus the area. A search for properties for sale in Pyrmont, NSW is one request and costs 1 credit.
curl "https://api.perceptlayer.com/v1/domain-com-au/search?mode=buy&suburb=Pyrmont&state=NSW&page=1" \
-H "X-API-Key: $API_KEY"
The recorded response, trimmed to the first listing:
{
"success": true,
"data": {
"mode": "buy",
"listing_type": "Sale",
"total_results": 85,
"total_pages": 9,
"page": 1,
"page_size": 10,
"listings": [
{
"listing_id": 2021264183,
"listing_slug": "48-1-5-harwood-street-pyrmont-nsw-2009-2021264183",
"display_address": "48/1-5 Harwood Street, Pyrmont",
"display_price": "For Sale $795,000 | …",
"bedrooms": 1,
"bathrooms": 1,
"carspaces": 1,
"property_type": "ApartmentUnitFlat",
"agency": {
"name": "Ray White Pyrmont",
"agency_id": 36143,
"logo_url": "…"
}
},
…
],
…
},
"meta": {
"billable": true
}
}
Two things to note. display_price is text as the portal shows it, so a second listing in the same response reads Auction Guide: $1,100,000. Parse it before you treat it as a number. And property_type is a portal label (ApartmentUnitFlat), not the Apartment value you pass in property_types[].
The response also has a facets object. In this recording it says facet counts aren't available, so don't plan on counting by bedroom from the API alone; filter instead.
Which search parameters are available?
All filters are optional except mode. Lists use the [] form, repeated for each value.
| Parameter | Type | Notes |
|---|---|---|
mode |
string | Required: buy, rent, sold, new-homes, commercial, rural |
suburb, suburbs[] |
string, list | Up to 80 characters each |
region, state, postcode |
string | state up to 40, postcode up to 10 characters |
page |
integer | Page number |
property_types[] |
list | House, Apartment, Townhouse, Land, Rural, NewApartments, NewHomeDesigns, NewHouseLand |
listing_attributes[] |
list | HasPhotos, HasPrice, HasMatterport, NotUpForAuction, MarkedAsNew, NotUnderContract |
min_bedrooms, max_bedrooms |
integer | Bedroom range |
min_bathrooms, max_bathrooms |
integer | Bathroom range |
min_carspaces, max_carspaces |
integer | Car space range |
min_price, max_price |
integer | Price range |
min_land_area, max_land_area |
integer | Land area range |
sold_date_range |
string | ALL, LAST_WEEK, LAST_MONTH, LAST_THREE_MONTHS, LAST_SIX_MONTHS, LAST_YEAR, LAST_TWO_YEARS |
For recent sales, switch the mode and add a date range:
curl "https://api.perceptlayer.com/v1/domain-com-au/search?mode=sold&suburb=Pyrmont&state=NSW&sold_date_range=LAST_THREE_MONTHS" \
-H "X-API-Key: $API_KEY"
If you're unsure how a suburb is spelled or slugged, locations takes a q string and optional mode (sale or rent) and channel, and resolves it first.
How do you get one property from a listing?
Pass the listing_id or the listing_slug from a search result to property. Both parameters are optional in the schema, but you need one of them, so a typical flow is search first, then one detail call per listing you care about. Each detail call is 1 credit.
curl "https://api.perceptlayer.com/v1/domain-com-au/property?listing_id=2021264183" \
-H "X-API-Key: $API_KEY"
We haven't recorded a property response for this guide, so we won't list its fields here. The Property endpoint page has a playground where you can run it with your key and see the real fields before you write a parser.
Budget for this pattern. A search page returns a batch of listings in one credit, then each detail call is another. Pulling detail for every listing on one 10-listing page costs 1 + 10 = 11 credits.
How do you get auction results and suburb insights?
auction-results takes one required parameter, city, and suburb-insights takes bedrooms and property_type. Each is a single call at 1 credit, which makes them cheap context to attach to a search.
curl "https://api.perceptlayer.com/v1/domain-com-au/auction-results?city=Sydney" \
-H "X-API-Key: $API_KEY"
For suburb insights, pick a suburb by slug, or give a bounding box with top_left[latitude], top_left[longitude], bottom_right[latitude] and bottom_right[longitude]. property_type is Unit or House, a different vocabulary from the search filter.
curl -G "https://api.perceptlayer.com/v1/domain-com-au/suburb-insights" \
--data-urlencode "slug=$SUBURB_SLUG" \
--data-urlencode "bedrooms=2" \
--data-urlencode "property_type=Unit" \
-H "X-API-Key: $API_KEY"
Set SUBURB_SLUG to the suburb's slug, which you can look up with locations. A bad parameter returns invalid_parameters (422) and costs nothing; see the errors docs.
We haven't recorded responses for these two endpoints either. Run them in the playground on the Domain.com.au API page to see which fields come back for your suburb.
Domain.com.au or realestate.com.au: which should you call?
Call Domain.com.au when you want its listing fields, auction results by city or suburb insights. Call realestate.com.au when you want its listing shape, agency ratings or its sales events. For many projects the answer is both, because the two portals return different fields for a listing.
The difference shows in the recorded responses. Domain's search listing is flat: display_price, bedrooms, carspaces and an agency with an agency_id. The realestate.com.au search listing is nested: counts sit under features (for example features.bedrooms.value), the address is split into address.suburb, address.state and address.postcode, and the listing company carries ratingsReviews with avgRating and totalReviews.
| Need | Domain.com.au | realestate.com.au |
|---|---|---|
| Search by area | search with mode, suburb, state |
search with location, channel |
| One property | property by listing_id or slug |
property by url |
| Auction data | auction-results by city |
sales-events by state or url |
| Suburb data | suburb-insights |
suburb-profile by url |
| Agent and agency | agent, agency by slug |
agent-profile, agency-profile by url |
Note how the lookups differ. Domain's detail calls take IDs and slugs, while realestate.com.au's take full url values, which you copy from a search result's url field. Here is the realestate.com.au equivalent of the Pyrmont call, using its own parameter names:
curl "https://api.perceptlayer.com/v1/realestate-com-au/search?location=Sydney%2C+NSW&channel=buy&page=1" \
-H "X-API-Key: $API_KEY"
A trimmed excerpt of its recorded response:
{
"success": true,
"data": {
"channel": "buy",
"location": "Sydney, NSW",
"total_results": 596,
"listings": [
{
"id": "149311860",
"url": "https://www.realestate.com.au/property-apartment-nsw-sydney-149311860",
"property_type": "Apartment",
"address": {
"suburb": "Sydney",
"state": "NSW",
"postcode": "2000"
},
"price": "Contact Agent",
"features": {
"bedrooms": { "value": 2 },
…
},
…
},
…
],
…
}
}
Because the portals use different IDs, you can't join listings on an ID. Match on address instead; the article on deduplicating listings across sources covers that.
What does it cost, and what are the limits?
Every endpoint here is 1 credit per successful call. Failed calls cost nothing and return X-Credits-Used: 0. Free accounts get 1,000 credits every month after verifying an email, with no credit card, and the credits docs explain how they're counted.
Worked examples, all at 1 credit a call:
- One suburb sweep, using the recorded Pyrmont result: 9 pages × 1 credit = 9 credits.
- That sweep plus a
propertycall for each of its 85 listings: 9 + 85 = 94 credits. - The same 94-credit job run weekly for 4 weeks: 4 × 94 = 376 credits, inside the free 1,000.
- 20,000 calls × 1 credit = 20,000 credits, which fits the 50,000-credit Build pack. See pricing for what credits cost.
Rate limits are per account: free accounts get 1 request a second (60 a minute). A 429 carries a Retry-After header with the seconds to wait, as do 503 responses. Requests have no idempotency key, so a request that timed out on your side may still have been billed. The rate limits docs show how to read the RateLimit-* headers.
When should you use Domain's official API instead?
If you need something beyond reading public listings, such as managing listings you hold, use Domain's own developer program. Its developer portal lists API packages such as Agents & Listings, Listing Management, Price Estimation and Properties & Locations, with sandbox testing before you go live. Perceptlayer fits the read-only case: one key, JSON from public listing pages, and a free key after you verify an email address. It also puts both Australian portals behind the same key and the same response envelope. Data is collected from publicly available sources and returned as found at the time of the call, so check it against the portal if a decision depends on it.
For the next step, run a search in the playground with your key, or see the wider real estate APIs. If you're comparing how other markets look, the Rightmove API guide does the same for the UK.
APIs in this post
Frequently asked questions
Is there a Domain.com.au API I can call with a free key?
Yes. With a Perceptlayer key you call https://api.perceptlayer.com/v1/domain-com-au/... directly, sending the key in X-API-Key. Free accounts get 1,000 credits a month after email verification, and each endpoint call is 1 credit. Domain's own developer program is a separate product with its own sign-up.
How do I get all pages of a suburb search?
Read total_pages from the first response and loop page from 1 to that number. In the recorded Pyrmont search, total_results was 85 and total_pages was 9, so a full pull is 9 calls and 9 credits. Stay under your account's request rate, and honour Retry-After on a 429.
How do I search sold properties?
Set mode=sold on search and add sold_date_range, which accepts ALL, LAST_WEEK, LAST_MONTH, LAST_THREE_MONTHS, LAST_SIX_MONTHS, LAST_YEAR or LAST_TWO_YEARS. You can combine it with suburb, state, property_types[] and the bedroom filters. The call costs 1 credit like any other.
What happens if a call fails?
You aren't charged. Errors return an HTTP status and a JSON body with error.code, error.message and request_id, and the response carries X-Credits-Used: 0. Codes include invalid_parameters (422), rate_limited (429) and source_error (502); the errors docs list the rest and what to do for each.
Can an AI agent call these endpoints?
Yes. The MCP server at https://api.perceptlayer.com/mcp exposes search_endpoints, get_endpoint and call_endpoint. The first two only look up the catalogue and cost nothing; call_endpoint spends the endpoint's 1 credit on success only. Setup is in the AI agents docs.