Skip to content

Kashlei Hotels for developers

Hotel availability and rates API

Keep rooms, prices, minimum stay and closed dates on Kashlei in sync from your PMS, channel manager or your own scripts, as often as you like.

Works with any system

The API is plain HTTPS and JSON, so any PMS, channel manager, revenue tool or spreadsheet script can use it. Native connectors for Agilysys and Oracle OPERA Cloud (OHIP) are coming; until then, use this API or a channel manager that can call it.

Prefer files? Upload a CSV or Excel sheet (up to 50,000 rows) in the Calendar tab of the hotel dashboard.

Authentication

  1. Open the API access tab in the hotel dashboard and click Generate key. Copy it: it's shown once.
  2. Send it on every request: Authorization: Bearer khk_…
  3. Each key works for one property only. You can have several active keys (for example one per system), rotate them, or revoke them at any time.

Kashlei stores only a hash of each key. Keep keys on your server; never put them in a web page or app. Calls without a valid key get 401.

Base URL

https://kashlei.com/api/hotels/v1

Dates are YYYY-MM-DD nights (the night of that date). Prices are in US cents. You can refer to a room type by its Kashlei roomTypeId or by your own roomCode (set codes in the API access tab).

GET /room-types

Lists your room types with their Kashlei IDs and your room codes.

curl https://kashlei.com/api/hotels/v1/room-types \
  -H "Authorization: Bearer $KASHLEI_API_KEY"
{
  "propertyId": "cm2x…",
  "roomTypes": [
    { "id": "cm2r…", "code": "DLXK", "name": "Deluxe King", "maxGuests": 2,
      "defaultRooms": 12, "active": true, "ratePlanId": "cm2p…" }
  ]
}

GET /inventory

Current availability, bookings, price, minimum stay and closed flag per night. from and to are inclusive, up to 366 nights. Optional roomTypeId or roomCode filter.

curl "https://kashlei.com/api/hotels/v1/inventory?from=2026-11-01&to=2026-11-30&roomCode=DLXK" \
  -H "Authorization: Bearer $KASHLEI_API_KEY"
{
  "propertyId": "cm2x…", "from": "2026-11-01", "to": "2026-11-30", "currency": "usd",
  "roomTypes": [
    { "roomTypeId": "cm2r…", "code": "DLXK",
      "days": [ { "date": "2026-11-01", "availableRooms": 12, "bookedRooms": 3,
                  "priceCents": 14900, "closed": false, "minStay": 1 } ] }
  ]
}

POST or PUT /inventory (batch update)

Send up to 500 room-nights per call (a range counts once per night per room type). Each update has a room, a date or a from/to range, and any of:

  • availableRooms: rooms you want to sell that night (0–2000). Can't go below rooms already booked.
  • priceCents: nightly price in cents ($10.00–$50,000.00).
  • minStay: minimum nights for stays arriving that night (1–60).
  • closed: true to stop selling, false to reopen.

Fields you leave out stay unchanged. The whole batch is applied in one transaction: if any update is invalid or would go below booked rooms, nothing changes and you get every error back. Every change is recorded in your hotel's audit log.

curl -X POST https://kashlei.com/api/hotels/v1/inventory \
  -H "Authorization: Bearer $KASHLEI_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: sync-2026-11-01T0900-0001" \
  -d '{
    "updates": [
      { "roomCode": "DLXK", "from": "2026-11-01", "to": "2026-11-07",
        "availableRooms": 8, "priceCents": 15900, "minStay": 2 },
      { "roomTypeId": "cm2r…", "date": "2026-11-24", "closed": true }
    ]
  }'
{ "ok": true, "updatedNights": 8, "batchId": "hb_…" }

Dates can be from yesterday up to 500 days ahead. A room-night may appear only once per batch.

Idempotency

Add an Idempotency-Key header (16–64 letters, digits, _ or -) to batch updates. If you retry with the same key and body within 24 hours, you get the original response (with Idempotent-Replayed: true) and nothing is applied twice. Reusing a key with a different body returns 409.

Rate limits

60 requests per minute per property, across all its keys. That's enough for a full sync every few minutes; most hotels sync 10–100 times a day. Over the limit you get 429 with a Retry-After header. Use GET /ping to check a key without changing anything.

Errors

Errors are JSON: { "error": "code", … }.

HTTPerrorMeaning
400invalid_jsonThe body isn't valid JSON.
401unauthorizedMissing, malformed or revoked key.
403kyc_required, operator_suspended, property_suspended …Your hotel account can't make changes right now (same rules as the dashboard).
404not_found / feature_disabledUnknown endpoint, or Kashlei Hotels is switched off.
405method_not_allowedWrong HTTP method for this endpoint.
409below_bookedAvailable rooms would drop below rooms already booked. Response lists the conflicting nights; nothing was changed.
409idempotency_conflictThat Idempotency-Key was already used with a different body.
413request_too_largeBody over 512 KB.
422validation_failedOne or more updates are invalid. errors[] gives the index and reason of each; nothing was changed.
422invalid_dates / range_too_long / room_not_foundBad query parameters on a read.
429rate_limitedMore than 60 requests in a minute for this property. Retry after the Retry-After seconds.
503hotels_unavailableTemporary problem on our side. Retry with the same Idempotency-Key.
HTTP/1.1 422
{ "error": "validation_failed",
  "errors": [ { "index": 1, "error": "invalid_price", "field": "price" } ] }

Activity log and webhook

The API access tab shows your last 50 calls with their status. Already using the signed ARI webhook (POST /api/hotels/channel/ari)? It keeps working; the bearer API is the self-serve option with bigger batches. Questions? See the partner page.