Skip to content
Docs
FA
Sign in
Start here
  • Overview
  • Quickstart
  • Concepts
Collect data
  • Designing events
  • Event dictionary
  • Placing events
  • Identity
  • Web SDK
  • Android SDK
  • Devices and push
  • Server to server
  • Product catalogue
  • Webhooks
Engage customers
  • Segments
  • Journeys
  • Transactional
  • Consent and caps
  • In-app and inbox
Analyze and export
  • Reports and exports
Developer reference
  • API reference
    • Ingest endpoints
    • Management API
  • Errors
  • Limits
  • OpenAPI
Developer tools
  • MCP server
  • Working with an agent
Privacy and changes
  • Personal data
  • Versioning

The OpenAPI document

A machine-readable description of both surfaces, for generating a client, testing, or feeding a tool.

Both customer-facing surfaces are described in one machine-readable file: 41 paths, 48 operations and 65 schemas, in OpenAPI 3.1.1.

#Download

Shell
curl -O https://segmentic.net/openapi.json

The file is rebuilt with every build of this site, from the same repository the API lives in. So the copy you download is always the one these pages describe, rather than a hand-maintained duplicate that was updated once and then fell behind.

There is no second file with a .yaml extension and there does not need to be. JSON is a subset of YAML 1.2, so any tool that wants YAML accepts this file unchanged.

#What is in it

Every route a customer calls, on both hosts:

  • Ingest, https://in.segmentic.net: events, batches, device registration, web push, messengers, the inbox, on-site messages, inbound webhooks, and the four routes we put inside messages ourselves.
  • Management, https://api.segmentic.net: key identity, capabilities, the event and trait schema, audiences, segments, campaigns, server-side ingest, exports, funnel and retention reports, and transactional messages.

Every operation carries a summary, complete request and response schemas with the real field names, and every status code with its error body. Every operation but POST /v1/messenger/unlink also carries a description, and every one but the six operations behind the four routes we put inside messages carries at least one worked example taken from the project's own tests.

Two authentication schemes are defined and neither is a document-wide default, so 39 of the 48 operations declare exactly one of them:

Name in the fileWhat it isWhere
writeKeyhttp with scheme: bearer. The write key, wk_seg_ plus 43 charactersIngest host routes
managementKeyhttp with scheme: bearer. The API key, sk_seg_ plus 43 charactersManagement host routes

The other nine declare security: []: GET /v1/status, POST /v1/hooks/{source}/{token}, POST /v1/bounce/{local}, and the six operations behind the four routes we put inside messages.

Three error shapes sit in components, because the server genuinely has three: IngestError, flat with status and message, on the ingest host; and PublicError, nested, alongside FlatError and FlatCodedError on the management host. Each response points at the one that actually comes back.

#Two hosts in one document

One structural point that is confusing if nobody tells you.

Both hosts serve paths under /v1, and an OpenAPI document keys paths by string. So the two surfaces share one paths map, and every operation carries its own servers array with exactly one entry, plus a tag naming its surface.

The one exception is GET /v1/status, which genuinely exists on both hosts, so it is a single operation carrying both servers.

If your tool applies the document's first server to everything, half your requests go to the wrong host. Tools that read operation-level servers (current openapi-generator, Postman, Insomnia, Bruno, Kiota) handle it correctly.

#Generating a client

TypeScript client
npx @hey-api/openapi-ts -i https://segmentic.net/openapi.json -o src/segmentic
Go, Python or PHP client
npx @openapitools/openapi-generator-cli generate \
  -i https://segmentic.net/openapi.json \
  -g go \
  -o ./segmentic-client

A client generated from this document has two authentication classes, because the document has two. Give the wk_seg_ key to the ingest operations and the sk_seg_ key to the management ones. The other way round compiles and fails at runtime with 401.

#Loading it into a tool

Postman, Insomnia and Bruno all import straight from a URL: choose the URL option on import and give it https://segmentic.net/openapi.json. Create the environment variables yourself, because no key is in the document and none should be.

For contract testing, schemathesis works directly against the ingest surface:

Shell
schemathesis run https://segmentic.net/openapi.json \
  --base-url https://in.segmentic.net \
  --header "Authorization: Bearer wk_seg_..."

This writes real events to a real account. Create a separate app with its own key first, or your test data mixes into your real data and separating them afterwards is difficult.

#What is not in it

  • The panel's own API. That surface is not for customers, is not stable, and changes weekly. What is here is what is promised to be stable.
  • Any route that mints a key. Those live on a different listener that is not addressable from outside. Get a key from the panel; the quickstart shows how.
  • Rules that no type can express. That context.screen is accepted and stored nowhere, that a timestamp older than thirty days on POST /v1/events is silently pulled to the edge of the window, that an unknown export format becomes ndjson: all of these live in a field's description and no schema can enforce them. A generated client stops none of them.
  • What goes inside an export's spec. POST /v1/exports passes that field through untouched and validates nothing in it. Its keys differ per kind and no document in this repository enumerates them. That is a real gap rather than an omission in the file.
  • Pagination, because it does not work, and the document says so. limit is read only on GET /v1/exports, cursor nowhere, and has_more is always false. The two list routes are cut at 200 rows by the query underneath, ordered by most recently edited, with nothing in the response saying the rest exist.

Four routes are in the file that you never call: the open pixel, the unsubscribe page, the preference centre and the short-link redirect. Those are URLs we put inside messages, opened by a mail client or a handset. They carry security: [], which means "no key is needed" rather than "this is open": the signature inside the URL is the credential. Their behaviour is described in consent and caps.

The pagination point is one of two things the document's own info description states plainly. The other is that error shapes are not uniform on the management host: eleven routes reuse the panel's handlers and answer {"error": "a string"} rather than the coded envelope, so your client must treat error as either a string or an object before reading error.code. The details are in error codes.

#When the API changes

Rule 7 of the repository says a change to these two surfaces carries its documentation in the same change, and a check in CI enforces it: a route that is registered and not in the reference turns the build red, apart from the four in-message URLs above and four more the script lists by name. The other direction is checked as a code sample rather than as prose, because a page is allowed to tell you a route does not exist and several usefully do. The exact rule is in versioning and changes. Because this file is built from the same repository, it cannot fall behind the reference either. The full account is in versioning and changes.

PreviousLimitsNextMCP server

On this page

  • Download
  • What is in it
  • Two hosts in one document
  • Generating a client
  • Loading it into a tool
  • What is not in it
  • When the API changes

Segmentic

This page is written from the code