Request Headers
The X-Dz-* request headers that drive attribution, session identity and per-request routing, and the two headers the gateway returns.
Request Headers
Gateway controls ride X-Dz-* request headers rather than the request body, so
every official vendor SDK can drive them through a first-class, typed parameter
(default_headers and its equivalents).
Every X-Dz-* request header is stripped before the request is forwarded
upstream. The provider never sees them.
What there is to send
Every header is optional, and they fall into three groups:
- Attribution --
X-Dz-User,X-Dz-Team,X-Dz-Project,X-Dz-EnvandX-Dz-Labelslabel a request so its cost can be attributed to someone. - Source --
X-Dz-Namespace,X-Dz-WorkloadandX-Dz-Podrecord where a request came from, for correlating gateway traffic with the workload that produced it. - Behavioural --
X-Dz-Session-Id,X-Dz-Workload-TypeandX-Dz-Routerchange what the gateway does with the request rather than how it is labelled.
Each header's exact value and rules are on the operation that accepts it in the API reference, generated from the contract. The rest of this page is the part the contract cannot carry: which of them are worth sending, and why.
Why the session id is worth sending
The session is the unit of this domain. It is resolved in precedence order:
- The
X-Dz-Session-Idheader you supplied. - A session id extracted from a recognised client surface.
- Auto-inference from the source pod, the system-prompt hash and a credential salt, within a sliding window.
Only the first is a stable session key -- one that came from you and is therefore comparable across turns. An inferred identity is recorded separately and never substituted for a client-supplied one, because it fragments a conversation: a reconnecting client presents the same conversation under a new identity, so an absent prior turn says nothing about whether a warm prefix existed.
Anything that reasons about a previous turn -- cache-miss classification,
cross-turn cache-bust pricing, holdout arm stickiness -- requires a stable
session key and falls back to "unknown" rather than guessing. Sending
X-Dz-Session-Id is the single cheapest thing you can do to improve the
quality of your own measurements.
X-Dz-Router rules
The routing override is accepted on exactly one carrier per request, and the failure modes are all refusals rather than silent fallbacks:
| Situation | Result |
|---|---|
| Sent once, valid JSON, known fields | Applied as the most specific rung of the routing ladder. |
Sent on the header and as the dz_router body field | 400 dz_router_conflict, even if the two are byte-identical. There is no precedence rule. |
| Sent twice as a repeated header | 400 invalid_dz_router. |
| Over 8192 bytes | 400 dz_router_too_large, with a message pointing at routing profiles -- the server-side mechanism for large steering configurations. |
| Carrying an unknown field | Refused, not ignored (invalid_dz_router). A typo must never silently do nothing. |
Response headers
Keyed inference responses carry two headers:
| Header | Value |
|---|---|
X-Dz-Request-Id | The id the trace and telemetry rows for this request are stored under. |
X-Cache | MISS, HIT or SEMANTIC-HIT. Stamped MISS before the cache is consulted and overwritten by whichever hit path serves, so the value is exhaustive. |
Both are emitted on keyed inference only. Passthrough traffic is forwarded byte-identically in both directions, so nothing is added there.