{
  "openapi": "3.0.1",
  "info": {
    "title": "Airbnb Calendar & Occupancy Scraper: Occupancy Rate, Revenue",
    "description": "Airbnb availability calendar (12-13 months), occupancy rate and revenue estimates for listing URLs/IDs or a whole area. One flat row per listing plus day-by-day calendar. Charged per listing, not per day.",
    "version": "0.1",
    "x-build-id": "QrNUX8W3WQ58KvvN3"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/thelastscraper~airbnb-calendar-occupancy/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-thelastscraper-airbnb-calendar-occupancy",
        "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/thelastscraper~airbnb-calendar-occupancy/runs": {
      "post": {
        "operationId": "runs-sync-thelastscraper-airbnb-calendar-occupancy",
        "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/thelastscraper~airbnb-calendar-occupancy/run-sync": {
      "post": {
        "operationId": "run-sync-thelastscraper-airbnb-calendar-occupancy",
        "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": {
          "actorVariant": {
            "title": "Actor variant",
            "type": "string",
            "description": "Internal: which Store Actor this is (do not change).",
            "default": "calendar-occupancy"
          },
          "where": {
            "title": "Listings or area: listing URLs/IDs, neighborhoods, cities or Airbnb search URLs",
            "type": "array",
            "description": "One per line: a listing URL (https://www.airbnb.com/rooms/123) or ID, a place as you would type it on Airbnb (\"Dubai Marina, Dubai\") or an Airbnb search URL. Places are resolved with their real OpenStreetMap boundary.",
            "items": {
              "type": "string"
            }
          },
          "calendarMonths": {
            "title": "Calendar months",
            "enum": [
              "12",
              "13"
            ],
            "type": "string",
            "description": "12 months = one request per listing: the next 30/60/90 days are complete and the 365-day window stays empty (Airbnb's calendar starts on the 1st of the current month). 13 months = one more small request (~16 KB) and the full 365-day window.",
            "default": "12"
          },
          "calendarDays": {
            "title": "Daily calendar rows",
            "type": "boolean",
            "description": "One row per listing and day in the 'calendar' dataset (about 365 per listing): available, check-in/check-out allowed, minimum and maximum nights. Charged as calendar-days: $0.25 per 1,000 listing-months, so $3.00 per 1,000 listings for 12 months. Off: only the occupancy row per listing.",
            "default": true
          },
          "includeListingDetails": {
            "title": "Also deliver the full listing record",
            "type": "boolean",
            "description": "Every occupancy row is built from the listing's page and price quote, so each listing is charged as listing details plus calendar. On: the full listing record too (description, amenities, host, rules, permit, price breakdown) in the 'listings' dataset, at no extra charge.",
            "default": false
          },
          "checkIn": {
            "title": "Check-in date",
            "pattern": "^(\\d{4})-(0[1-9]|1[0-2])-(0[1-9]|[12]\\d|3[01])$",
            "type": "string",
            "description": "YYYY-MM-DD. Used to quote the price that feeds the revenue estimate (ADR). Empty = automatic dates (30 days from today, 5 nights). For an area, the default 'Which listings' (All active listings) searches without dates and quotes every listing for these dates; with 'Only listings available on your dates', the search uses these dates and returns only the homes still free on those nights."
          },
          "checkOut": {
            "title": "Check-out date",
            "pattern": "^(\\d{4})-(0[1-9]|1[0-2])-(0[1-9]|[12]\\d|3[01])$",
            "type": "string",
            "description": "YYYY-MM-DD, after the check-in date. Empty with an empty check-in = automatic dates (each record says so in scrape.dates_auto)."
          },
          "adults": {
            "title": "Adults",
            "minimum": 0,
            "maximum": 16,
            "type": "integer",
            "description": "Adult guests. Airbnb keeps the listings that accommodate at least this many people (4 also brings listings for 5, 6 or more guests) and quotes each price for exactly this party. 0 = any number of guests: no capacity filter, each price quoted for one guest (cannot be combined with Children).",
            "default": 2
          },
          "children": {
            "title": "Children",
            "minimum": 0,
            "maximum": 15,
            "type": "integer",
            "description": "Ages 2-12. They count toward the listing's capacity like adults and pay the extra-guest fee in the quote.",
            "default": 0
          },
          "infants": {
            "title": "Infants",
            "minimum": 0,
            "maximum": 5,
            "type": "integer",
            "description": "Under 2. They do not count toward capacity and stay free.",
            "default": 0
          },
          "pets": {
            "title": "Pets",
            "minimum": 0,
            "maximum": 5,
            "type": "integer",
            "description": "Only pet-friendly listings are returned, and the quote includes the host's pet fee (folded into the nightly rate).",
            "default": 0
          },
          "currency": {
            "title": "Currency",
            "pattern": "^[A-Z]{3}$",
            "type": "string",
            "description": "ISO 4217 code (default USD). All amounts are returned as numbers in this currency; it also replaces the currency of an Airbnb search URL.",
            "default": "USD"
          },
          "maxListings": {
            "title": "Max listings",
            "minimum": 0,
            "type": "integer",
            "description": "Stop after this many listings (areas can have thousands). 0 = no limit.",
            "default": 200
          },
          "coverage": {
            "title": "Which listings",
            "enum": [
              "all",
              "available"
            ],
            "type": "string",
            "description": "All listings (default): every active listing in the area, found with a search without dates and quoted for your dates; homes already booked on your dates are included, which is what keeps occupancy unbiased. Only available: a search with your dates (fewer listings, cheaper), but it misses exactly the homes that are booked, so area occupancy comes out too low."
          },
          "bedroomsExact": {
            "title": "Exactly N bedrooms",
            "minimum": 0,
            "type": "integer",
            "description": "Keep only listings with exactly this many bedrooms. Airbnb only filters by minimum, so the Actor asks Airbnb for at least this many and checks the exact number on each search card or, when the card does not show it (in Europe a search without dates shows the host type there instead), on the listing page. Listings that do not match are not delivered or charged."
          },
          "minBedrooms": {
            "title": "Min bedrooms",
            "minimum": 0,
            "type": "integer",
            "description": "Airbnb's own filter (\"N or more\")."
          },
          "minBathrooms": {
            "title": "Min bathrooms",
            "minimum": 0,
            "type": "number",
            "description": "Airbnb's own filter (\"N or more\"); half bathrooms count as 0.5."
          },
          "minBeds": {
            "title": "Min beds",
            "minimum": 0,
            "type": "integer",
            "description": "Airbnb's own filter (\"N or more\")."
          },
          "roomTypes": {
            "title": "Type of place",
            "type": "array",
            "description": "Leave empty for any type.",
            "items": {
              "type": "string",
              "enum": [
                "Entire home/apt",
                "Private room",
                "Shared room",
                "Hotel room"
              ],
              "enumTitles": [
                "Entire home / apartment",
                "Private room",
                "Shared room",
                "Hotel room"
              ]
            }
          },
          "amenities": {
            "title": "Amenities",
            "type": "array",
            "description": "Keep only listings with ALL the amenities picked (Airbnb's own filter). With listing URLs or IDs the Actor checks them on the listing page; what the page cannot confirm is kept with a FILTER_UNVERIFIED warning. Amenity ids of other markets work inside an Airbnb search URL (amenities[]=...).",
            "items": {
              "type": "string",
              "enum": [
                "Wifi",
                "Air conditioning",
                "Pool",
                "Kitchen",
                "Free parking",
                "Smoking allowed",
                "Gym",
                "Breakfast",
                "Hot tub",
                "Indoor fireplace",
                "Heating",
                "Washer",
                "Dryer",
                "Smoke alarm",
                "Carbon monoxide alarm",
                "Hair dryer",
                "Iron",
                "Dedicated workspace",
                "Self check-in",
                "TV",
                "EV charger",
                "BBQ grill",
                "Step-free access",
                "Guest entrance wider than 32 inches",
                "Disabled parking spot",
                "Step-free bedroom access",
                "Bedroom entrance wider than 32 inches",
                "Step-free bathroom access",
                "Bathroom entrance wider than 32 inches",
                "Crib",
                "Ceiling or mobile hoist",
                "Shower grab bar",
                "Toilet grab bar",
                "Step-free shower",
                "Shower or bath chair",
                "King bed"
              ]
            }
          },
          "freeCancellation": {
            "title": "Free cancellation only",
            "type": "boolean",
            "description": "Keep only listings with free cancellation for your dates (Airbnb's own filter; with listing URLs or IDs, checked on the cancellation policy).",
            "default": false
          },
          "proxyStrategy": {
            "title": "Proxy strategy",
            "enum": [
              "auto",
              "datacenter",
              "residential"
            ],
            "type": "string",
            "description": "Auto (recommended): starts with Apify datacenter proxies and switches to residential proxies only if Airbnb starts blocking (2 blocks in the last 50 requests: a request blocked on 2 datacenter IPs makes its third attempt through residential); after 300 clean requests on residential it tries datacenter once more. If residential proxies are not available to the run, it slows down instead. Datacenter / Residential: always that kind. Proxy traffic is not billed to you separately: the event prices include it. The log, the status message and the OUTPUT record show requests, blocks and estimated traffic per proxy level.",
            "default": "auto"
          },
          "proxyCountry": {
            "title": "Residential proxy country",
            "pattern": "^([A-Za-z]{2})?$",
            "type": "string",
            "description": "Optional 2-letter country code for residential proxies. Empty = US, like the datacenter proxies: Airbnb shows totals before taxes to visitors outside the EU, so every run's prices mean the same. An EU country (e.g. DE) makes Airbnb show totals with taxes (the taxes column fills in). Prices are always in the selected currency."
          },
          "omitPersonalData": {
            "title": "Omit personal data",
            "type": "boolean",
            "description": "Only matters with 'Also deliver the full listing record' (the occupancy rows have no host or reviewer fields): host and co-host names, photos and bios are set to null and the host's name is replaced with \"the host\" in Airbnb-generated texts. GDPR-friendly. Business data (ratings, Superhost, years hosting, license numbers) stays.",
            "default": false
          },
          "maxConcurrency": {
            "title": "Parallel listings",
            "minimum": 20,
            "maximum": 32,
            "type": "integer",
            "description": "Listings scraped at the same time, each through its own Apify Proxy IP with its own pause (a listing's price quote, policies and calendar are requested together with its page, as a browser loads it). 20 to 32; the default, 32, scrapes about 5 listings a second with the default 4 GB of memory. The minimum keeps a run's duration, which the event prices include, bounded. With your own proxy URLs or without a proxy (one IP), the pause is shared and more parallel listings are not faster.",
            "default": 32
          },
          "delaySeconds": {
            "title": "Pause between requests",
            "minimum": 1,
            "maximum": 2,
            "type": "integer",
            "description": "Minimum seconds between two requests from the same IP (plus up to 1 s of random jitter); a listing's quote, policies and calendar go out with its page. 1 (the default, the fastest) or 2. If Airbnb blocks, the Actor slows down and changes proxies by itself.",
            "default": 1
          },
          "maxRequests": {
            "title": "Max requests to Airbnb",
            "minimum": 0,
            "type": "integer",
            "description": "Hard cap on requests to airbnb.com for the whole run (retries included). 0 = no cap.",
            "default": 0
          }
        }
      },
      "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
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}