{
  "openapi": "3.0.1",
  "info": {
    "title": "Redfin Scraper — Listings + Agent Database (Email & Phone)",
    "description": "Redfin scraper with an instant agent database — 11,400+ agents, all 50 states, email + phone + deal stats, uncapped. Filter by State/City/Brokerage, no scraping needed. Or live-scrape search URLs, property details, agents & emails across sale, sold & rental. Pure HTTP. JSON/CSV.",
    "version": "0.0",
    "x-build-id": "5K5KhsNO4GkbvdfAm"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/memo23~apify-redfin-cheerio-ppe/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-memo23-apify-redfin-cheerio-ppe",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    },
    "/acts/memo23~apify-redfin-cheerio-ppe/runs": {
      "post": {
        "operationId": "runs-sync-memo23-apify-redfin-cheerio-ppe",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor and returns information about the initiated run in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/runsResponseSchema"
                }
              }
            }
          }
        }
      }
    },
    "/acts/memo23~apify-redfin-cheerio-ppe/run-sync": {
      "post": {
        "operationId": "run-sync-memo23-apify-redfin-cheerio-ppe",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "inputSchema": {
        "type": "object",
        "properties": {
          "dbState": {
            "title": "State (2-letter code)",
            "type": "string",
            "description": "The US state to pull agents for — e.g. FL, CA, TX. Setting this alone delivers instant database results."
          },
          "dbCity": {
            "title": "City / region (optional)",
            "type": "string",
            "description": "Narrow to a city or service region (case-insensitive substring). Leave empty to return the whole state."
          },
          "dbBrokerage": {
            "title": "Brokerage contains (optional)",
            "type": "string",
            "description": "Only return agents whose brokerage name contains this text (case-insensitive), e.g. \"Redfin\" or \"Compass\"."
          },
          "dbHasEmail": {
            "title": "Only agents with an email",
            "type": "boolean",
            "description": "Return only agents that have an email address on file.",
            "default": false
          },
          "dbHasPhone": {
            "title": "Only agents with a phone",
            "type": "boolean",
            "description": "Return only agents that have a phone number on file.",
            "default": false
          },
          "instantDatabase": {
            "title": "Use Instant Database (no scraping)",
            "type": "boolean",
            "description": "Serve results from the pre-collected database instead of live-scraping. Auto-enabled when you set a State / City / Brokerage above.",
            "default": false
          },
          "startUrls": {
            "title": "Start URLs",
            "type": "array",
            "description": "URLs to start with — Redfin search pages (city / neighborhood / zip, with or without /filter/…) or individual property / agent pages. Optional when using searchKeyword + searchMode.\n\n**Advanced (optional):** instead of a plain URL, an entry can be an object carrying per-URL options — `{ \"url\": \"https://…\", \"headers\": { … }, \"userData\": { … } }`. Headers are sent with that request; `userData` is echoed back on that URL's output records (handy for tagging which search produced which listings). Paste it as-is into a row here, or pass it as a real object via the API — both work.",
            "items": {
              "type": "string"
            }
          },
          "searchKeyword": {
            "title": "Search keyword (e.g. Los Angeles)",
            "type": "string",
            "description": "Optional Redfin search phrase such as a city, ZIP code, or neighborhood. When set, the actor resolves it through Redfin autocomplete before crawling."
          },
          "searchMode": {
            "title": "Search Mode",
            "enum": [
              "sale",
              "rent",
              "sold"
            ],
            "type": "string",
            "description": "Mode used with searchKeyword.",
            "default": "sale"
          },
          "soldTimeframe": {
            "title": "Sold Timeframe",
            "enum": [
              "1mo",
              "3mo",
              "6mo",
              "1yr"
            ],
            "type": "string",
            "description": "Sold-history window used when searchMode is sold.",
            "default": "1mo"
          },
          "flattenOutput": {
            "title": "Flatten Output Structure",
            "type": "boolean",
            "description": "Set to true to output a flat data structure.",
            "default": false
          },
          "fields": {
            "title": "Keep only these fields",
            "uniqueItems": true,
            "type": "array",
            "description": "Whitelist of fields to keep in each property record — everything else is dropped. Leave empty to return the full object. Supports nested paths like `streetAddress.assembledAddress`; naming a parent (e.g. `streetAddress`) keeps all of its sub-fields. `url` is always included. Example: url, listingPrice, streetAddress, city, postalCode, latLong, sqFt, beds, baths, lotSize.",
            "items": {
              "type": "string"
            }
          },
          "excludeFields": {
            "title": "Drop these fields",
            "uniqueItems": true,
            "type": "array",
            "description": "Blacklist of fields to remove from each property record — applied after the whitelist. Handy to strip heavy blocks you never use, e.g. airData, fireData, fireDataV2, floodData, floodDataV2, heatData, heatDataV2, windData, noticePlacement, pageExperimentInfo, recommendedAgent. Supports nested paths.",
            "items": {
              "type": "string"
            }
          },
          "includesAboveTheFoldData": {
            "title": "Includes Above The Fold Data",
            "type": "boolean",
            "description": "Include address, basic region info, and media.",
            "default": true
          },
          "includesBelowTheFoldData": {
            "title": "Includes Below The Fold Data",
            "type": "boolean",
            "description": "Include neighborhood, transit, and schools.",
            "default": true
          },
          "includesParcelBounds": {
            "title": "Includes Parcel Bounds",
            "type": "boolean",
            "description": "Include property boundaries and APN data.",
            "default": true
          },
          "includesBannerData": {
            "title": "Includes Banner Data",
            "type": "boolean",
            "description": "Include current promotions or banners.",
            "default": true
          },
          "includesAmenitiesData": {
            "title": "Includes Amenities Data",
            "type": "boolean",
            "description": "Include community and unit amenities.",
            "default": true
          },
          "includesWalkScoreData": {
            "title": "Includes Walk Score Data",
            "type": "boolean",
            "description": "Include walk, transit, and bike scores.",
            "default": true
          },
          "includesSellsideThresholdData": {
            "title": "Includes Sellside Threshold Data",
            "type": "boolean",
            "description": "Include price drop info.",
            "default": true
          },
          "includesFloorPlansData": {
            "title": "Includes Floor Plans Data",
            "type": "boolean",
            "description": "Include bed/bath units and floor plan structures.",
            "default": true
          },
          "includesProtoHomeData": {
            "title": "Includes Proto Home Data",
            "type": "boolean",
            "description": "Include companion Redfin proto-home enrichment when available.",
            "default": true
          },
          "includeProfileDetails": {
            "title": "Include Profile Details",
            "type": "boolean",
            "description": "Include detailed profile information in the output.",
            "default": false
          },
          "enrichEmails": {
            "title": "Enrich with contact emails (experimental)",
            "type": "boolean",
            "description": "If enabled, finds a contact email for each result from its own website (or by discovering it from the name). Adds contactEmail + contactWebsite columns plus a detailed emailEnrichment object. Best-effort.",
            "default": false
          },
          "includeMarketSummary": {
            "title": "Add a market summary record",
            "type": "boolean",
            "description": "When enabled, appends ONE extra summary record at the end of the run with market analytics computed across all scraped listings: total count, median / average / min / max price, median price-per-sqft, median beds & baths, median days-on-market, and counts broken down by property type, city and zip. Great for market tracking and valuation benchmarking. Computed from data already scraped — no extra requests.",
            "default": false
          },
          "maxItems": {
            "title": "Max number of listings/items per crawl/scrape",
            "minimum": 0,
            "type": "integer",
            "description": "Maximum number of listings/items that will be scraped. 0 means no cap: the run delivers as many as its max cost per run affords and stops when that budget is reached.",
            "default": 1000
          },
          "monitoringMode": {
            "title": "🔄 Monitoring mode (only new listings vs. previous runs)",
            "type": "boolean",
            "description": "If checked, only listings not seen in previous runs are scraped — a daily/weekly delta feed without re-paying for the same properties. Requires a paid Apify plan.",
            "default": false
          },
          "detectPriceChanges": {
            "title": "📉 Detect price changes across runs (needs monitoring mode)",
            "type": "boolean",
            "description": "Requires \"monitoring mode\". Tracks each listing's price and reports every change across runs — one row per move with <code>oldPrice</code>, <code>newPrice</code>, <code>priceDelta</code>, <code>pctChange</code>, <code>direction</code> and <code>firstSeenAt</code>. Rows go to a separate run dataset <code>redfin-changes-&lt;runId&gt;</code> (not the default output), billed at the low <code>additional-data</code> rate. No effect unless monitoring mode is on.",
            "default": false
          },
          "detectRemovedListings": {
            "title": "🗑️ Detect removed / sold listings across runs (needs monitoring mode)",
            "type": "boolean",
            "description": "Requires \"monitoring mode\". Reports listings that have LEFT the market (sold/off-market) since your previous run — one <code>{ \"status\": \"removed\", propertyId, url, searchUrl, detectedRemovedAt }</code> row each, to a separate run dataset <code>redfin-removed-&lt;runId&gt;</code>, billed at the low <code>additional-data</code> rate. <b>Needs a full scan:</b> set <code>maxItems</code> high enough to cover the whole search — runs that stop early are skipped so nothing is wrongly flagged. No effect unless monitoring mode is on.",
            "default": false
          },
          "maxConcurrency": {
            "title": "Max Concurrency",
            "type": "integer",
            "description": "Maximum number of pages that can be processed at the same time.",
            "default": 50
          },
          "minConcurrency": {
            "title": "Min Concurrency",
            "type": "integer",
            "description": "Minimum number of pages that will be processed at the same time.",
            "default": 1
          },
          "maxRequestRetries": {
            "title": "Max Request Retries",
            "type": "integer",
            "description": "Number of times the crawler will retry a failed request before giving up.",
            "default": 100
          },
          "storeName": {
            "title": "Name your storage for listings (deduplication and long-term retention)",
            "type": "string",
            "description": "Assign a custom name to the Key-Value Store where your scraped listings will be saved. This ensures:\n 1. **Data Deduplication**: Prevents duplicate entries in the storage. \n 2. **Persistent Storage**: Enables long-term retention of listings, beyond default storage limits.\n 3. **Project Management**: Separate datasets by using unique names for different projects or analyses.\n 4. **Data Reuse**: Easily reference and reuse stored data without overwriting.\n (If left blank, the default storage will be used with standard retention limits.)"
          },
          "proxy": {
            "title": "Proxy configuration (optional override)",
            "type": "object",
            "description": "Leave empty — the actor routes all traffic through its own built-in proxy at no extra cost to you (dedicated ISP proxies on paid Apify plans, US residential proxies on the free plan). Only set this if you want to use your own proxies; on the free plan, anything you set here replaces the built-in residential proxy."
          }
        }
      },
      "runsResponseSchema": {
        "type": "object",
        "properties": {
          "data": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "actId": {
                "type": "string"
              },
              "userId": {
                "type": "string"
              },
              "startedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "finishedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "status": {
                "type": "string",
                "example": "READY"
              },
              "meta": {
                "type": "object",
                "properties": {
                  "origin": {
                    "type": "string",
                    "example": "API"
                  },
                  "userAgent": {
                    "type": "string"
                  }
                }
              },
              "stats": {
                "type": "object",
                "properties": {
                  "inputBodyLen": {
                    "type": "integer",
                    "example": 2000
                  },
                  "rebootCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "restartCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "resurrectCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "computeUnits": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "options": {
                "type": "object",
                "properties": {
                  "build": {
                    "type": "string",
                    "example": "latest"
                  },
                  "timeoutSecs": {
                    "type": "integer",
                    "example": 300
                  },
                  "memoryMbytes": {
                    "type": "integer",
                    "example": 1024
                  },
                  "diskMbytes": {
                    "type": "integer",
                    "example": 2048
                  }
                }
              },
              "buildId": {
                "type": "string"
              },
              "defaultKeyValueStoreId": {
                "type": "string"
              },
              "defaultDatasetId": {
                "type": "string"
              },
              "defaultRequestQueueId": {
                "type": "string"
              },
              "buildNumber": {
                "type": "string",
                "example": "1.0.0"
              },
              "containerUrl": {
                "type": "string"
              },
              "usage": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "integer",
                    "example": 1
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_UNBLOCKER_UNITS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "usageTotalUsd": {
                "type": "number",
                "example": 0.00005
              },
              "usageUsd": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "number",
                    "example": 0.00005
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_UNBLOCKER_UNITS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}