Documentation 29
Zendesk API quickstart
A support desk with real tickets in it.
A Zendesk Support v2-compatible host for the simulated org. Point node-zendesk or zenpy at it with a base-URL swap and walk the desk: tickets with their comments and audits, the people who filed them, the companies those people work at, the groups that route them, the macros and triggers and views that move them, search, tags and the incremental exports. The outage ticket is about the same incident the observability hosts serve, filed by a person the CRM hosts serve, escalated to the engineer the pager woke.
Coverage, hosts and pinned snapshots for Zendesk — 281 of 342 read surfaces served and verified.
00 / Status
281 of 342 read endpoints are rendered.
01 / Base URL + auth
One origin, any credential.
Requests go to https://zendesk.sandboxapis.dev. Paths are Zendesk's own — /api/v2/…, with or without the .json suffix its clients append — so a client that builds https://yoursubdomain.zendesk.com only changes the origin it was already building. Auth is HTTP Basic; any value passes here, so there is no trial account to create and no API token to mint.
# answers on every generation
curl "https://zendesk.sandboxapis.dev/api/v2/locales.json"
# the ticket queue: hello-14 and later
curl "https://zendesk.sandboxapis.dev/api/v2/tickets.json?per_page=5"
# the desk's configuration: hello-15 and later
curl "https://zendesk.sandboxapis.dev/api/v2/macros.json"Using a key? Keys & rate limits → — a SandboxAPIs key rides the same Basic slot and lifts the anonymous limit.
02 / What this host serves
The desk, and the account around it.
Both of Zendesk's pagination grammars work, and the one you get is the one you ask for: send page and per_page for the offset envelope (count, next_page, previous_page), or page[size] and page[after] for the cursor envelope (meta, links). Both go null at the end of a collection, so a client that pages by following the link stops.
# the desk, newest updates first
curl "https://zendesk.sandboxapis.dev/api/v2/tickets/recent.json"
# one ticket, its thread, and the audit trail behind it.
# ids are per-universe, so take one from the list rather than typing it.
ID=$(curl -s "https://zendesk.sandboxapis.dev/api/v2/tickets.json?per_page=1" | jq -r '.tickets[0].id')
curl "https://zendesk.sandboxapis.dev/api/v2/tickets/$ID.json"
curl "https://zendesk.sandboxapis.dev/api/v2/tickets/$ID/comments.json"
curl "https://zendesk.sandboxapis.dev/api/v2/tickets/$ID/audits.json"
# the people and the companies they work at
curl "https://zendesk.sandboxapis.dev/api/v2/users.json?role=agent"
curl "https://zendesk.sandboxapis.dev/api/v2/organizations.json"
# the rules that route the queue
curl "https://zendesk.sandboxapis.dev/api/v2/macros.json"
curl "https://zendesk.sandboxapis.dev/api/v2/views.json"
curl "https://zendesk.sandboxapis.dev/api/v2/triggers.json"
# search, tags, and the incremental export
curl "https://zendesk.sandboxapis.dev/api/v2/search.json?query=type:ticket%20status:open"
curl "https://zendesk.sandboxapis.dev/api/v2/incremental/tickets.json?start_time=0"One user space, two kinds of person. Zendesk models agents and end users in a single space told apart by role, and so does this host: the org's own support and sales staff come back as agent or admin, the people at customer companies as end-user with an organization_id that resolves. An agent has no organization, and asking for theirs returns an empty list rather than an error — the question is valid and the answer is “none”.
03 / The join
The ticket is about the incident.
A ticket filed during an outage carries the incident's id in external_id — Zendesk's own field for linking a ticket to a local record — and that id is the one pd.sandboxapis.dev serves as an incident and sentry.sandboxapis.dev serves an error group for. GET /api/v2/tickets?external_id=… walks it the other way, from the outage to the tickets it caused. /api/v2/tickets/{id}/related carries jira_issue_ids, the tracker row engineering actually opened. A cross-provider test asserts every one of those hops against the other host rather than against this one.
04 / Pinning
Each pin keeps the generation it was frozen on.
05 / What is coming
The add-on surfaces.
61 rows do not serve, and each is classified in the coverage manifest with the reason. The families with nothing served at all are . Alongside them sit partly-served families whose remaining rows have a decided ruling rather than a promise: the OAuth registries answer 200 with an empty collection, because nobody ever registered a client on this account, and the by-id rows under them are a documented refusal for the same reason — no id can resolve. Everything else carries a proposed ruling awaiting review rather than a guess. Compare this host against the rest of the fleet →