Appearance
Changelog & deprecation policy
The compatibility covenant
/v1 evolves additively. A response may gain a field and a request may gain an optional one, at any time, without notice. So:
- Ignore unknown fields. A client that rejects a response because it carries a field the client has not seen will break on the next additive release. Parse what you need, ignore the rest.
- Never depend on field order or on the absence of a field.
- A field is never removed or re-typed in
/v1. Removing or re-typing a field is a breaking change, and breaking changes only ever land under a new major version (/v2) — never in place. A contract-snapshot test fails CI if a/v1field is removed or re-typed, so the covenant is enforced, not just promised.
The same rule governs the WebSocket protocol and the error-code enum: additive only, versioned in the auth ack (v), removals deferred to a new major.
Deprecation
When something must eventually go, it is deprecated first, not deleted. A deprecated surface keeps working, is marked in this changelog and in the spec, and is removed only after a notice window of at least ninety days — and only in a new major version, never in /v1.
Versioning
The info.version field in /openapi.json tracks the API contract, not our software release. Read it this way:
- A purely additive change within
/v1— a new endpoint, a new optional field — bumps the minor (1.1.0,1.2.0, …). - The major bumps only alongside a breaking
/v2surface, and never before one exists. - It is deliberately not the npm package version. SDK generators stamp
info.versioninto the version of the client they emit, so it has to mean "which contract" — not "which build of our server."
Deployment status is never carried by the version string. Whether a given environment is live, and what code it runs, is told by the servers block and by GET /deployment — not by info.version.
Reading changes
The machine-readable source of truth is /openapi.json: diff it between releases to see exactly what changed. Each reference page is stamped with the contract version it documents, so you can tell whether the reference in front of you describes the surface you are calling.
Releases
Dated entries land here as the API changes. Today the public API is on testnet; nothing here is an offer, a solicitation, or advice.
1.4.0 — 2026-08-20
Additive. GET /v1/markets/:id/candles: each candle may carry volumeContracts — fills-derived contracts traded in the bucket, the same basis as stats24h (basis: "fills"), over exactly the bar's window. A served value — including "0" — is the true sum; an absent field means the deployment cannot tell (pre-launch index-history bars carry none). prints is unchanged and remains a print count, not volume.
1.3.0 — 2026-08-20
Additive. GET /v1/markets/:id/candles: limit maximum raised from 1000 to 1440 — one UTC day of the 1m base in a single request, which is exactly what a full ninety-six-bar fifteen-minute frame aggregates from. Defaults unchanged.
1.2.0 — 2026-08-20
Additive. GET /v1/markets/:id/candles with interval=86400: each candle may carry seeded: true, marking a pre-launch index history bar — daily OHLC taken from the market's own oracle source before this venue's first print (prints is 0 on such bars). A bar without the field is a real bar folded from venue prints. Clients that render candles should render seeded bars visibly distinct; clients that ignore unknown fields are unaffected. Only the daily interval ever carries the field.
1.1.0 — 2026-08-20
Additive. GET /v1/markets/:id/candles:
intervalnow also accepts3600and86400(seconds, as ever). These are permanent server-side rollups of the same oracle-print fold;60remains the default and keeps a retention window of four days. Aggregate intermediate frames (5m/15m/4h) client-side from the nearest served base.limitmaximum raised from 96 to 1000. The default stays 96; requests that never sendlimitorintervalsee identical behavior to 1.0.0.