{
  "openapi": "3.1.0",
  "info": {
    "title": "Spare Keys Stay apartments",
    "version": "1.1.0",
    "description": "Search 19 whole furnished apartments in Boston (Dorchester, Hyde Park): free parking, full kitchen. With dates: live availability and the exact checkout total, with and without code BOOKDIRECT (20% off nights, applied automatically on the site). Facts: sparekeysstay.com/llms-full.txt",
    "contact": { "name": "Daryl Creese (owner)", "url": "https://sparekeysstay.com/" }
  },
  "servers": [ { "url": "https://sparekeysstay.com" } ],
  "paths": {
    "/api/ai-inventory": {
      "get": {
        "operationId": "searchApartments",
        "summary": "Find apartments for a Boston trip, with live availability and totals for given dates",
        "description": "Without dates: apartments that fit, with facts. With check_in and check_out: only those open for the whole stay; the first 6 priced live. A group too big for one apartment gets apartments_together: the fewest apartments at one address that sleep everyone.",
        "parameters": [
          { "name": "guests", "in": "query", "required": false, "description": "Number of guests, 1-30. One apartment sleeps up to 10; more means several apartments at one address (19 Ellis Street sleeps 29, 17 Ellis Street next door 25).", "schema": { "type": "integer", "minimum": 1, "maximum": 30 } },
          { "name": "bedrooms", "in": "query", "required": false, "description": "At least this many bedrooms (1-4).", "schema": { "type": "integer", "minimum": 1, "maximum": 4 } },
          { "name": "neighborhood", "in": "query", "required": false, "description": "Boston neighborhood.", "schema": { "type": "string", "enum": ["dorchester", "hyde-park"] } },
          { "name": "trip_type", "in": "query", "required": false, "description": "hospital: closest to the Longwood hospitals first. sports, concert: closest to TD Garden. family: crib first. monthly: washer and dryer only. group: apartments together. tonight: tonight in Boston.", "schema": { "type": "string", "enum": ["hospital", "sports", "concert", "family", "monthly", "group", "tonight"] } },
          { "name": "near", "in": "query", "required": false, "description": "Sort by typical drive time outside rush hour. longwood = Boston Children's, Dana-Farber, Brigham and Women's, Beth Israel; bmc = Boston Medical Center; mgh = Mass General; gillette = Foxborough; logan = the airport.", "schema": { "type": "string", "enum": ["bmc", "tufts", "longwood", "mgh", "downtown", "td-garden", "fenway", "gillette", "logan"] } },
          { "name": "laundry", "in": "query", "required": false, "description": "true = only apartments with a washer and dryer inside (16 of 19).", "schema": { "type": "boolean" } },
          { "name": "first", "in": "query", "required": false, "description": "Apartment slug to pin first if it fits.", "schema": { "type": "string" } },
          { "name": "check_in", "in": "query", "required": false, "description": "Arrival date, YYYY-MM-DD (Boston). Up to a year ahead.", "schema": { "type": "string", "format": "date" } },
          { "name": "check_out", "in": "query", "required": false, "description": "Departure date, YYYY-MM-DD, after check_in.", "schema": { "type": "string", "format": "date" } }
        ],
        "responses": {
          "200": {
            "description": "Matching apartments",
            "content": { "application/json": { "schema": { "$ref": "#/components/schemas/SearchResult" } } }
          },
          "400": {
            "description": "A parameter was not understood",
            "content": { "application/json": { "schema": { "type": "object", "properties": { "error": { "type": "string" }, "docs": { "type": "string" } } } } }
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "SearchResult": {
        "type": "object",
        "properties": {
          "source": { "type": "string" },
          "as_of": { "type": "string", "format": "date-time" },
          "query": {
            "type": "object",
            "description": "The search as understood, after aliases and defaults.",
            "properties": {
              "guests": { "type": ["integer", "null"] },
              "bedrooms": { "type": ["integer", "null"] },
              "neighborhood": { "type": ["string", "null"] },
              "trip_type": { "type": ["string", "null"] },
              "near": { "type": ["string", "null"] },
              "laundry": { "type": ["boolean", "null"] },
              "first": { "type": ["string", "null"] },
              "check_in": { "type": ["string", "null"] },
              "check_out": { "type": ["string", "null"] }
            }
          },
          "how_to_book": { "type": "string" },
          "contact": { "type": "object", "properties": { "name": { "type": "string" }, "phone": { "type": "string" } } },
          "count": { "type": "integer" },
          "apartments": { "type": "array", "items": { "$ref": "#/components/schemas/Apartment" } },
          "apartments_together": { "type": "array", "items": { "$ref": "#/components/schemas/Together" } },
          "notes": { "type": "array", "items": { "type": "string" } },
          "more": { "type": "string" }
        }
      },
      "Apartment": {
        "type": "object",
        "properties": {
          "slug": { "type": "string" },
          "name": { "type": "string" },
          "url": { "type": "string", "description": "The apartment's page: photos, live calendar and booking." },
          "neighborhood": { "type": "string" },
          "building": { "type": "string" },
          "postal_code": { "type": "string" },
          "bedrooms": { "type": "integer" },
          "bathrooms": { "type": "number" },
          "sleeps": { "type": "integer" },
          "beds": { "type": "string" },
          "washer_dryer": { "type": "boolean" },
          "parking": { "type": "string" },
          "check_in": { "type": "string" },
          "check_in_time": { "type": "string" },
          "check_out_time": { "type": "string" },
          "self_check_in": { "type": "boolean" },
          "crib": { "type": "boolean" },
          "children_welcome": { "type": "boolean" },
          "pets": { "type": "boolean" },
          "smoking": { "type": "boolean" },
          "events": { "type": "boolean" },
          "train": { "type": "string" },
          "drive_times": { "type": "object", "additionalProperties": { "type": "string" } },
          "minutes_to_near": { "type": "array", "items": { "type": "integer" }, "description": "Typical drive in minutes [low, high] to the place sorted by." },
          "same_building": {
            "type": "array",
            "items": { "type": "object", "properties": { "slug": { "type": "string" }, "name": { "type": "string" }, "sleeps": { "type": "integer" } } }
          },
          "building_sleeps": { "type": "integer", "description": "How many the whole address sleeps." },
          "next_door": {
            "type": ["object", "null"],
            "properties": { "building": { "type": "string" }, "apartments": { "type": "integer" }, "sleeps": { "type": "integer" } }
          },
          "good_for": { "type": "array", "items": { "type": "string" } },
          "availability": { "$ref": "#/components/schemas/Availability" }
        }
      },
      "Availability": {
        "type": "object",
        "properties": {
          "status": { "type": "string" },
          "check_in": { "type": "string" },
          "check_out": { "type": "string" },
          "nights": { "type": "integer" },
          "total_usd": { "type": ["number", "null"], "description": "Whole stay, taxes and fees included, without a code." },
          "total_with_bookdirect_usd": { "type": ["number", "null"], "description": "Whole stay with code BOOKDIRECT, taxes and fees included - what the booking box shows." },
          "per_night_with_bookdirect_usd": { "type": ["number", "null"], "description": "total_with_bookdirect_usd divided by the nights: an all-in average with cleaning and taxes, not the nightly rate." },
          "taxes_and_fees_included": { "type": "boolean" },
          "note": { "type": "string" }
        }
      },
      "Together": {
        "type": "object",
        "description": "Several apartments booked for the same dates - at one address, or two buildings next door to each other.",
        "properties": {
          "buildings": { "type": "array", "items": { "type": "string" } },
          "neighborhood": { "type": "string" },
          "apartments": { "type": "array", "items": { "type": "string" } },
          "names": { "type": "array", "items": { "type": "string" } },
          "urls": { "type": "array", "items": { "type": "string" } },
          "sleeps_together": { "type": "integer" },
          "bedrooms_together": { "type": "integer" },
          "note": { "type": "string" },
          "availability": { "$ref": "#/components/schemas/Availability" }
        }
      }
    }
  }
}
