Use cases at a glance
New listing alerts are the backbone of any real estate investment workflow. Catching deals before the competition requires instant notification the moment a property matching your criteria hits the market. OpenClaw agents excel at this pattern: poll a data source on a schedule, filter by your criteria, deduplicate against previous results, and route alerts to your inbox or Slack.
New deal in target zip
Alert the moment a listing appears in your primary investment area—no waiting for MLS digest emails.
Price reduction spotted
A property just listed, then dropped price 6 hours later. Catch the reduction before other investors.
Just listed in a neighborhood
Monitor a specific street or a 0.5-mile radius. Get notified of any new inventory in that micro-market.
High-potential fixer alert
Filter for properties listed >20% below Zestimate. Likely fixer-uppers with meat on the bone.
Open house this weekend
Alert on listings with an open house event in the next 7 days in your target market.
Pre-foreclosure pipeline
When paired with foreclosure data sources, get notified of pre-foreclosure filings in target zips.
API setup: Zillow via RapidAPI
The Zillow RapidAPI gives you access to current listing data, including address, price, bed/bath count, square footage, Zestimate, and days on market. The data refreshes every 1–4 hours depending on your market's MLS syndication frequency.
Getting your RapidAPI key
- Visit
rapidapi.com/apimaker/api/zillow-com1and sign up for a free account. - Select the Basic plan (~$30/month) to avoid rate limits on polling.
- Navigate to your dashboard and copy the
X-RapidAPI-Keyheader value. - Store it in your
secrets.envfile asRAPIDAPI_KEY=your_key_here. - Never commit
secrets.envto version control.
The RapidAPI free tier allows 50 calls/month—enough for light testing. For production monitoring of multiple zip codes with hourly polling, you need at least the Basic plan.
Defining your search criteria
Effective listing alerts depend entirely on your filter configuration. Too broad and you'll drown in noise; too narrow and you'll miss opportunities. Here are the core filters available through the Zillow API:
| Filter | Example Value | Notes |
|---|---|---|
zip_codes |
90210, 90211, 10001 | Comma-separated list. Supports 1-10 zips per API call. Chain multiple calls for broader coverage. |
max_price |
750000 | Upper price bound. Omit for no limit. Filters to listings ≤ this amount. |
min_price |
200000 | Lower price bound. Screens out unlisted or data-error listings. |
min_beds |
2 | Minimum bedroom count. SFRs and multi-fam. Ignores studios and 1BR. |
min_baths |
1 | Minimum full baths. Reduces fixer-upper false positives. |
max_dom |
1 | Max days on market. Set to 1 for truly new listings only. Set to 3–7 for "recent" inventory. |
min_sqft |
1200 | Minimum livable square footage. Filters out tiny units in dense areas. |
property_type |
Single Family, Condo | Accepted values: Single Family, Condo, Townhouse, Multi-Family (2-4 units). |
max_price_per_sqft |
550 | Derived filter: price ÷ sqft. Useful for benchmarking against market comps. |
A practical example: you're investing in Austin, TX zips 78704 and 78723 with a $600k budget, targeting SFRs of 2000+ sqft listed in the past 24 hours. You'd configure:
zip_codes: "78704,78723"
min_price: 400000
max_price: 600000
min_beds: 3
min_baths: 2
min_sqft: 2000
max_dom: 1
property_type: "Single Family"
max_price_per_sqft: 300
This filters to reasonably-priced, spacious homes, eliminating penny stocks and paper deals.
New listing polling agent
The polling agent runs on a HEARTBEAT schedule, hits the Zillow API with your criteria, and compares results to a persistent store of previously-seen listings. Only truly new listings trigger alerts.
Here's the agent configuration in AGENTS.md format:
---
name: new-listing-alert
schedule: "0 */3 * * *" # Every 3 hours
tools:
- zillow-rapidapi
config:
search_params:
zip_codes: ["78704", "78723"]
min_price: 400000
max_price: 600000
min_beds: 3
min_baths: 2
min_sqft: 2000
max_dom: 1
property_type: "Single Family"
max_price_per_sqft: 300
deduplication:
store_type: "redis" # or "local_file"
store_path: "/data/seen_listings.json"
retention_days: 30
output:
channels: ["slack", "email"]
slack:
webhook_url: "${SLACK_WEBHOOK_URL}"
template: "listing_alert.jinja"
email:
to: "investor@example.com"
from: "alerts@openclaw.ai"
subject: "🏠 New listing alert: {address}"
---
job: |
results = await zillow_rapidapi.search(config.search_params)
new_listings = filter_new(results, config.deduplication)
for listing in new_listings:
send_alert(listing, config.output)
store_seen_listing(listing, config.deduplication)
The agent maintains a persistent record of every zpid (Zillow property ID) it has seen. On each run, it fetches current listings and compares zpids against the seen store. Only missing zpids are treated as new and trigger alerts. After 30 days, zpids are cleared from the seen store (allowing re-alerts if a property is re-listed after expiring).
Deduplication — only alert on truly new listings
Without deduplication, your agent would alert on the same listing every 3 hours indefinitely. Deduplication is the critical difference between a useful tool and alert fatigue.
Zpid-based deduplication
Each Zillow listing has a unique zpid (Zillow property ID). Your agent stores every zpid it has processed:
{
"zpids_seen": {
"12345678": "2026-03-25T14:30:00Z",
"87654321": "2026-03-25T12:00:00Z"
}
}
On each run, the agent compares the API response zpids against this set. New zpids = new listings. Once stored, a zpid is never alerted on again (until it expires from the retention window).
Storage backend: Redis vs. local file
Redis: Scales to millions of zpids, O(1) lookups. Required if monitoring 50+ zip codes or running agents across multiple servers.
Local file: JSON stored on disk. Fine for single-agent setups or <10 zip codes. Simple to backup and inspect.
Retention window
Set retention to 30 days: properties that de-list and re-list after 30 days trigger a new alert. This is intentional—a property cycling back to the market is a signal worth re-notifying on.
Alert formatting and routing
Once you've identified a new listing, the alert payload needs to be formatted and routed. Your agent supports Slack and email natively.
Slack alert template
{
"blocks": [
{
"type": "header",
"text": {
"type": "plain_text",
"text": ":house: New listing in 78704"
}
},
{
"type": "section",
"fields": [
{
"type": "mrkdwn",
"text": "*Address*\n123 Oak Street, Austin, TX 78704"
},
{
"type": "mrkdwn",
"text": "*Price*\n$549,500"
},
{
"type": "mrkdwn",
"text": "*Beds / Baths*\n3 BD / 2 BA"
},
{
"type": "mrkdwn",
"text": "*Sqft*\n2,150 sqft"
},
{
"type": "mrkdwn",
"text": "*DOM*\n1 day"
},
{
"type": "mrkdwn",
"text": "*Zestimate*\n$575,000"
}
]
},
{
"type": "section",
"text": {
"type": "mrkdwn",
"text": "*Analysis*\n• Listed 2.3% below Zestimate\n• Price per sqft: $255.81\n• Recently renovated kitchen (per listing)\n\n"
}
}
]
}
This formats the alert as a rich Slack card with headers, structured fields, and a direct link to the Zillow listing. Recipients see the critical data at a glance.
Email alert
For email subscribers, keep the format scannable:
Subject: 🏠 New listing: 123 Oak Street, Austin, TX 78704 — $549,500
Body:
─────────────────────────────────
NEW LISTING ALERT
─────────────────────────────────
Address: 123 Oak Street, Austin, TX 78704
List Price: $549,500
Beds / Baths: 3 BD / 2 BA
Square Feet: 2,150 sqft
Days on Market: 1
Zestimate: $575,000
Price vs ZH: -2.3%
Price/SqFt: $255.81
Analysis:
• Listed below Zestimate—potential opportunity
• Recently updated: new roof (2025), HVAC (2024)
• Open house Sat 10–2pm
View on Zillow:
https://www.zillow.com/homes/12345678
─────────────────────────────────
Filter Settings: 78704, 78723 | 3+ BD | $400k–$600k
Next Check: 03-25-2026 17:00 UTC
─────────────────────────────────
HEARTBEAT schedule
Set your polling agent to run on a HEARTBEAT schedule. The interval depends on your market's velocity and your risk tolerance.
Every 2 hours (0 */2 * * *): High-velocity markets (dense urban, competitive). Maximize odds of seeing deals before other investors.
Every 3 hours (0 */3 * * *): Default. Balances API cost and alert responsiveness. Recommended for most users.
Every 6 hours (0 */6 * * *): Budget-conscious or low-velocity markets. Acceptable lag for markets where new inventory doesn't turn over hourly.
Additionally, configure a morning digest at 0 8 * * * (8 AM daily) that collates all new listings from the past 24 hours and sends a single summary report. This prevents alert overload while preserving the option to scan the previous day's inventory in one go.
Sample alert output
Here's what you'd see in your Slack channel or email inbox:
FAQ
How often does Zillow update new listing data via the API?
Every 1–4 hours for most markets; brand new listings can take up to 24 hours to appear depending on MLS syndication speed. Set your polling interval to every 2–4 hours to balance freshness against API cost.
What filters should I use to avoid alert fatigue?
At minimum filter by: max days on market (e.g., ≤1), price range, bed/bath minimums, and zip code or radius. Adding a price-per-sqft threshold ($X/sqft max) dramatically reduces noise in competitive markets. Start conservative — you can loosen filters later.
Can I get alerts for pre-foreclosures or auctions?
Not through the Zillow RapidAPI feed. For pre-foreclosures and auctions, use ATTOM Data Solutions or PropStream. The listing alert pattern shown here applies to both, but those APIs require separate credentials and higher spend (~$100–300/month for ATTOM).
How do I avoid duplicate alerts if my agent crashes and restarts?
The zpid-based deduplication persists to a file or Redis instance outside the agent process. On restart, the agent immediately reloads the seen set, preventing re-alerts on previously-processed zpids. If you're concerned about edge cases, add a timestamp check: alert only if (current_time - listing_created_time) < 6 hours, ensuring you're surfacing truly fresh inventory.
Can I test the agent without going live to Slack?
Absolutely. Configure a dry-run mode in your agent: fetch results, deduplicate, print to console (not Slack). Once confident, flip dry_run: false and enable alerts. This is especially useful when tuning filters to avoid sending garbage alerts to your team.