API referencePublic · JSON · v1 implementation

Stay Quote API

Request an informational stay quote from Roomwicket’s saved hotel, room, offer, manually maintained quote exclusions, availability, and rate records.

This endpoint does not make a reservation. A returned quote is informational only: it is not a reservation, booking confirmation, payment-backed confirmation, availability guarantee, or room hold.

Method

POST

Endpoint

/api/stay-quote

01 · Request

Send strict JSON

The body must be a JSON object with the fields below. The endpoint rejects unknown fields, malformed JSON, and bodies that fail any validation rule with HTTP 400.

Stay quote request fields
FieldTypeContract
hotelIdstringRequired and non-empty after trimming.
roomTypeIdstring?Optional, but non-empty when supplied. Use this or offerId.
offerIdstring?Optional, but non-empty when supplied. Use this or roomTypeId.
checkInstringA real calendar date in YYYY-MM-DD format.
checkOutstringA real YYYY-MM-DD date after checkIn.
occupancy.adultsintegerRequired; from 1 through 20.
occupancy.childreninteger?From 0 through 20; defaults to 0.
occupancy.roomsinteger?From 1 through 10; defaults to 1.
Request body
{
  "hotelId": "hotel_123",
  "offerId": "offer_456",
  "checkIn": "2027-05-10",
  "checkOut": "2027-05-13",
  "occupancy": {
    "adults": 2
  }
}

At least one of roomTypeId or offerId is required.

The parsed response echoes a normalized request, so omitted children and rooms appear as 0 and 1.

02 · Responses

A quote or an honest unavailable result

A valid request returns HTTP 200. The response always contains the normalized request, the informational notice, and paymentBackedReservationConfirmation: "unavailable". The top-level status selects the result shape.

200 · quoted

Matching saved data produced a rate.

The quote object contains hotel (id, name, and optional contact email/phone), room (id and name), rate (amountMinor, currency, and unit of night or stay), and nullable offerTerms with id, title, summary, terms, and validThrough.

200 response · quoted
{
  "status": "quoted",
  "paymentBackedReservationConfirmation": "unavailable",
  "notice": "This quote is informational only. It is not a confirmed reservation or booking, does not guarantee availability, and is not payment-backed.",
  "request": {
    "hotelId": "hotel_123",
    "offerId": "offer_456",
    "checkIn": "2027-05-10",
    "checkOut": "2027-05-13",
    "occupancy": { "adults": 2, "children": 0, "rooms": 1 }
  },
  "quote": {
    "hotel": {
      "id": "hotel_123",
      "name": "Example hotel",
      "contact": { "email": "stay@example.invalid" }
    },
    "room": { "id": "room_789", "name": "Example room" },
    "rate": { "amountMinor": 45000, "currency": "USD", "unit": "stay" },
    "offerTerms": {
      "id": "offer_456",
      "title": "Example offer",
      "summary": "Saved offer summary",
      "terms": "Saved offer terms",
      "validThrough": "2027-06-30"
    }
  }
}
200 · unavailable

The request is valid, but it cannot be quoted.

This shape contains the exact reason, human-readable message, and matched references for hotel, room, and offerTerms. These references are nullable when a saved record did not match.

200 response · unavailable
{
  "status": "unavailable",
  "paymentBackedReservationConfirmation": "unavailable",
  "notice": "This quote is informational only. It is not a confirmed reservation or booking, does not guarantee availability, and is not payment-backed.",
  "request": {
    "hotelId": "hotel_123",
    "roomTypeId": "room_789",
    "checkIn": "2027-05-10",
    "checkOut": "2027-05-13",
    "occupancy": { "adults": 2, "children": 0, "rooms": 1 }
  },
  "reason": "availability_not_persisted",
  "message": "Saved availability is not available for this stay. Add persisted availability before quoting.",
  "matched": {
    "hotel": { "id": "hotel_123", "name": "Example hotel" },
    "room": { "id": "room_789", "name": "Example room" },
    "offerTerms": null
  }
}

Unavailable reasons

hotel_not_found
The requested hotel is not published or does not exist.
room_not_found
The requested room is not available for this hotel.
offer_not_found
The requested offer is not published or does not exist for this hotel.
offer_not_linked_to_room
The offer is not linked to a room.
offer_not_associated_with_room
The offer is not associated with the requested room.
offer_not_valid_for_stay
The saved offer terms do not cover the requested stay dates.
offer_blackout
A manually maintained quote exclusion covers the requested stay dates; this is not live inventory or a booking hold.
availability_not_persisted
Saved availability is not available for this stay.
stay_unavailable
Saved availability marks this stay as unavailable.
rate_not_persisted
A saved rate is not available for this stay.
400 · invalid request

The body failed strict validation.

The body is exactly error plus an issues array. Each issue contains a dot-separated path and the validator's message.

400 response
{
  "error": "Invalid stay quote request.",
  "issues": [
    { "path": "checkOut", "message": "Check-out must be after check-in." }
  ]
}

03 · Data and boundaries

What this endpoint can tell you

Saved-data quote

The resolver matches published hotel, room, and offer records, then uses persisted availability and rate data when present. A quoted result describes what those saved records support at request time; operator-entered blackout ranges are manually maintained quote exclusions, not live inventory.

No payment-backed reservation

The current response contract deliberately reports payment-backed reservation confirmation as unavailable. It does not claim a live PMS, channel, payment, booking, or room-hold integration.

Availability and rate data may be absent

When persisted availability is absent, the resolver can return availability_not_persisted. When availability is present but a persisted rate is absent, it can return rate_not_persisted. The current loader reads the published property, room, and offer records; it does not invent missing availability or rates.

The contract defines no additional rate, date-window, payload-size, or freshness limits. The field ranges and date ordering documented above are the validation rules shipped by the endpoint; they are not a guarantee that a stay can be held or booked.

Browse published hotels