TracePass
Reference

Authentication

API-key authentication, Idempotency-Key semantics, and per-plan rate limits for the v1 surface.

TracePass v1 uses one auth mechanism: a static API key passed as a Bearer token in the standardAuthorizationheader. Every write also accepts anIdempotency-Keyfor safe retries. Limits are per plan, per UTC day — available on every plan including Free, with per-day call caps that scale with the plan.

API keys

Mint keys at Developer → API keys in the dashboard. Keys are workspace-scoped: every key is tied to one workspace and inherits its plan, limits, and audit log. Keys carry the tp_prefix followed by an opaque random suffix — there's no separate live / test prefix, and no env-namespaced sandbox. Test against your Free or Basic workspace if you need a non-production environment.

Pass the key as a Bearer token on every request:

bash
curl -sS https://app.tracepass.eu/api/v1/products \
  -H "Authorization: Bearer tp_REDACTED_xxxxxxxxxxxx"

Idempotency-Key

Every POST, PATCH, and DELETE on the v1 surface accepts an Idempotency-Keyheader. Send a UUID v4 (or any opaque string ≤ 255 chars) per logical operation; the platform stores the first response for 24 hours and replays it if the same key + same workspace shows up again. Network retries become safe — you won't double-create a passport because your HTTP client retried on a transient 5xx.

bash
curl -sS https://app.tracepass.eu/api/v1/passports \
  -H "Authorization: Bearer tp_REDACTED_xxxxxxxxxxxx" \
  -H "Idempotency-Key: 7b4f1e2c-9a3d-4e5b-8c1a-2d3e4f5a6b7c" \
  -H "Content-Type: application/json" \
  -d '{ "productId": "...", "gs1": { "gtin": "...", "serialNumber": "..." } }'

Reusing the same key with a different request body returns422 Unprocessable Entity with error: "Idempotency-Key has already been used with a different request body. Use a new key for the new request, or reuse the original body." — the platform doesn't silently overwrite, because that's almost always a client bug. Generate a fresh key for genuinely new operations.

Rate limits

Two ceilings apply per UTC day, per workspace:

1. v1 write budget — `maxV1WritesPerDay`

Counts every POST / PATCH / DELETEon the v1 surface. Reads aren't budgeted on this counter.

2. v1 passport-read budget — `maxV1PassportsPerDay`

Counts every GETon the passport endpoints (single read + paginated list). Separate from the write budget so an ERP pushing updates doesn't starve your read quota and vice versa.

PlanWrites / dayPassport reads / day
Free100100
Basic200200
Starter350350
Growth500500
Scale1,0001,000
Pro2,0002,000
EnterpriseUnlimited (negotiated)Unlimited

When you hit either ceiling the response is 429 Too Many Requests with a body like { "error": "API rate limit: 500 writes/day via /api/v1. Currently 500 today; requested 1. Retry tomorrow (UTC) or upgrade your plan." }. The window resets at 00:00 UTC; we don't support rolling windows because they make the limit harder to reason about downstream.

A separate quota — maxDpps — caps total active DPPs in your workspace and is enforced via a 402 response with an overage_required body when the plan supports per-passport overage. See the Create a passport endpoint for the overage flow.

What we don't support (yet)

OAuth 2.0 client-credentials, scoped sub-keys, and IP allow-listing are all on the roadmap but not shipped. If you need any of them today, mint a new API key per integration so you can revoke at the integration level — that's the workaround.