Skip to content

Getting Started

Request Conventions

The rules that hold across every endpoint: addressing, pagination, idempotency, partial results, limits and timeouts.

Base URL and Versioning

All client endpoints live under a single versioned prefix. The version is in the path, so a future /api/v2 can appear without disturbing anything you have built.

Base URL
https://api.gatewaystream.com/api/v1

Requests and Responses

  • Request bodies are JSON and need Content-Type: application/json. Responses are always JSON, including errors.
  • Dates are YYYY-MM-DD. Timestamps are ISO 8601 with an offset.
  • Currencies are ISO 4217 three-letter codes; countries and nationalities are ISO 3166 two-letter codes.
  • Monetary amounts are JSON numbers in the stated currency's major unit — 164.00 is one hundred and sixty-four dollars, not cents.
  • Fields the API does not recognise are ignored, not rejected, so a misspelt optional field does nothing rather than failing. Check spelling against the endpoint's page.

Identifiers

propertyId
uuid optional
A Gateway Stream property id. Stable within an environment, meaningless across environments. Returned by /properties and /search.
rateKey
string optional
An opaque, single-use handle on one priced rate. Valid for about 30 minutes. Never parse it.
bookingId
uuid optional
A Gateway Stream booking. What /bookings/:id takes.
requestId
string optional
Carried on every error. Quote it when asking Gateway Stream about a specific failure.

Pagination

List endpoints are cursor-paginated. Ask for a page, and if there is more, the response carries a nextCursor; pass it back as cursor to continue. When nextCursor is absent, you have reached the end.

First page
curl "https://api.gatewaystream.com/api/v1/properties?limit=50" \
  -H "x-api-key: $GWS_KEY"
Next page
curl "https://api.gatewaystream.com/api/v1/properties?limit=50&cursor=eyJnd3MiOjUwfQ" \
  -H "x-api-key: $GWS_KEY"

Idempotency

POST /bookings requires an Idempotency-Key header: a value between 8 and 100 characters that is unique to that attempt to book. A UUID is the obvious choice.

Booking with an idempotency key
POST /api/v1/bookings HTTP/1.1
Host: api.gatewaystream.com
x-api-key: gws_sandbox_8f3c1d9a7b2e4056
Idempotency-Key: 3f0b2c19-8d44-4ee2-9f0a-77ab51c0d6e2
Content-Type: application/json
  • First request with a given key → 201 and the new booking.
  • A repeat of the same request with the same key → 200 and the same booking. Nothing is created twice.

So a timeout or a dropped connection is safe to retry: resend the identical body with the identical key. What is never safe is retrying with a new key, or a new rate key, after an ambiguous answer — see Book.

Partial Results, Not Failures

Search and property listing ask several sources at once. One being slow, switched off or broken does not fail the call: the results that arrived are returned, and meta.complete says whether anything may be missing.

meta.complete
"meta": { "complete": false }

meta.complete

true
boolean optional
Every source answered. The result is whole.
false
boolean optional
At least one source did not answer inside the request’s timeout, or failed. What came back is real, but some rates or hotels may be missing. It does not say which source, or why — try again, or raise timeoutMs on a search.

Show the rates you got and treat complete: false as “there may be more”, not as “there is nothing”. Blocking a whole page on one slow source is the most common avoidable mistake in an integration.

Timeouts

POST /search takes an optional timeoutMs — how long to wait for the sources, between 1 and 8000 milliseconds, defaulting to 2500. It is a budget, not a promise of speed: whatever has answered when it elapses is what you get.

Set your own HTTP client's timeout comfortably above it. A client timeout shorter than timeoutMs throws away results the server was about to return.

Rate Limits

Requests are rate-limited per key. Over the limit you get 429 with details.retryAfterSeconds; back off for that long rather than retrying immediately.

429 rate_limited
{
  "error": {
    "code": "rate_limited",
    "message": "Too many requests",
    "requestId": "req_01JD8QE2W8P4L7RN",
    "details": { "retryAfterSeconds": 60 }
  }
}

If your traffic pattern needs a higher ceiling, that is a conversation with Gateway Stream rather than something to work around with parallel keys.