401) and a ceiling you hit (429).
You need an API key for a sandbox workspace — Get access —
and one environment variable:
There is no SDK. Every sample here is the standard HTTP client of its own language against
the published contract — that is deliberate, and it is why the four scripts are the same length.
Or import the collection
If you would rather press Send than run a script, import the Postman collection — all 48 operations, foldered by tag, with the request bodies from this document already filled in. Set theapiKey variable, run Exchange your API key for a token once, and
every other request is authorized from the token it stores.
It is generated from the OpenAPI document and checked against it on every build, so it
cannot describe a contract we no longer serve. The document itself is at
/openapi/openapi.yaml if
your tooling would rather have that.
What the scripts do
1
Exchange the key for a token
POST /v1/token. The body is empty: the workspace, the environment and your scopes all come
from the key. Read sandbox in the response to confirm which tenancy you are in.2
Read your catalogue
GET /v1/properties. Empty on a fresh sandbox — that is the correct answer, not a failure.3
Push a property
PUT /v1/properties/{provider_id}, keyed by your own identifier, so a retry lands on
the same row.4
Register a webhook endpoint
PUT /v1/webhooks/endpoint. We POST a signed endpoint.challenge to the URL during this
call and your handler must echo it back — until it does, the endpoint is
pending_verification and nothing is delivered. Webhooks has the
verifier.The script
What you should see
- Step 1 returns
sandbox: trueand ascopearray. Ifsandboxisfalseyou hold a production key, and every contract call below will answer501 not_enabledafter authenticating and validating in full — see Environments. - Step 2 returns
{"items": [], "has_more": false}on a fresh sandbox. - Step 3 returns
result: "created"the first time andresult: "updated"every time after, because the URL carries your own identifier.publishableandmissingsay whether the property can go on sale — a first push usually comes backmissing: ["cover_photo", "photos"]. - Step 4 leaves the endpoint
pending_verificationunless your handler echoed the challenge. That is the one step you cannot complete without writing a receiver first.
When it does not work
Every one of those is a problem document with a
code to branch on —
Errors.