Search

↑↓ to move↵ to openesc to closetop 6 documentation results

Book a demoTry TokenTriage

In development · Explore the product preview. Join the launch list or book a walkthrough.

Browse docs

Wire dialects

Which providers cost code to support, which cost a line of config, and what a wire driver owns that a descriptor cannot change.

ExplanationLast updated

On this page

Your application speaks one request shape. Your providers between them speak several. A gateway either translates every pair, which multiplies, or it treats the shape as one axis of a provider’s identity and keeps the number of shapes small. This one does the second.

A dialect is a wire format: what a request body looks like, where the model id lives, how a streamed response is framed, and where usage counts appear in the reply. It is not the same thing as a provider. Twelve providers can speak one dialect and still bill under twelve different namespaces.

What the proxy accepts on the way in

The proxy recognises each shipped dialect on its own native paths. A client speaking any of them is matched, given an endpoint kind, governed and ledgered against that dialect’s default upstream: Anthropic’s /v1/messages, Bedrock’s /model/{id}/converse and Deepgram’s /v1/listen are each answered as themselves. The suite drives that last one as a client request, at Deepgram’s own path, and reads back a priced transcription row.

A path matching no registered dialect and endpoint is forwarded as a ledgered passthrough rather than rejected, so an unusual call still reaches your provider and still lands on a row.

Translation is narrower than recognition, and the difference is where the number two belongs. Two client formats can be translated onto an upstream that speaks something else:

Client format Paths Your client
openai /v1/chat/completions, /v1/responses, /v1/embeddings, and the rest of the /v1 surface any OpenAI SDK, or anything OpenAI-shaped
anthropic /v1/messages the Anthropic SDK, Claude Code

Those two reach four upstream dialects between them, openai, anthropic, gemini and bedrock, streaming and not. Gemini- and Bedrock-format requests are recognised and served on their own dialects, but they are translation targets rather than translation sources, which is a product decision to defer rather than a gap in the wire code.

What the drivers speak on the way out

The generated September 6 catalog snapshot counts 15 wire-dialect ids across 95 built-in provider descriptors. The generator resolves the dialect id declared by the compiled Go package; directory spelling is not the identity.

Driver Descriptors
anthropic 1
anthropic_vertex 1
assemblyai 1
bedrock 2
bfl 1
deepgram 1
elevenlabs 1
fal 1
gemini 3
openai 78
replicate 1
runway 1
soniox 1
stability 1
vertex_predict_embed 1

78 descriptors use the openai driver. Mock verification remains per endpoint cell; the provider reference names the ten descriptors with no gated cell.

What the driver owns and the descriptor cannot change

A descriptor refines a driver; it does not replace it. The split matters when you are deciding whether a provider you want is a config change or a feature request.

The driver owns the body shape it parses and emits, how a stream is framed and flushed, where the model id is spliced when a routing decision rewrites it, and where usage counts are read from in the response.

The descriptor overrides the path templates, any required query parameters, the mandatory headers, the auth scheme and the pricing namespace.

So a provider that speaks OpenAI’s body shape at an unusual URL is data. A provider that speaks a body shape nothing ships is code, and it is the single most common reason a provider appears in the uncovered list.

Where the model id lives

A request can carry its model in four places, and which one it uses decides what a routing rewrite is allowed to touch.

Where the model comes from Drivers What a routing rewrite does
the request body openai and anthropic (model), elevenlabs (model_id), assemblyai (speech_model), soniox (model) splices the one field
the URL path bedrock, gemini, anthropic_vertex, and stability for all but one of its operations rewrites the path and leaves the body byte-identical
the URL query deepgram (?model=) nothing to splice; the driver reads the model there for pricing
a multipart form field stability, for the one operation that carries its model in the form instead nothing to splice; the field is read for pricing

The multipart form field is the newest of the four, and it arrived with image generation. Two of the four carriers are worth knowing about for a different reason: a body with no model field would be corrupted by a splice, so the proxy checks which kind of driver it is holding and takes the path route when that is the truthful one. replicate is the case that resists the rule, and it says so rather than guessing: a submit carrying a version field is rewritable, and a submit whose model is the URL is relayed unchanged with the enforcement fields cleared.

Only the routable endpoint kinds are rewritten at all. Speech, audio and image requests are priced from wherever their model is carried and are not re-pointed at another model.

Two dialects on one request

A request that arrives in one client format and is routed to an upstream speaking another is a cross-dialect route. It is off out of the box, and streaming across a pair needs a second opt-in on top of the first. Both accepted client formats reach all four of those upstream dialects, and every parameter a translation could not carry across is named on the row it produced.

Because that is a property of the pair of dialects rather than of routing policy, it is documented here rather than under Routing. Cross-dialect translation has the config shape, which client formats reach which upstreams has the grid pair by pair, and what a translation drops has the inventory of what did not survive the crossing.

The dialect: field, and when you still write it

An upstream configured with provider: derives its dialect from the descriptor, so you leave dialect: out. Setting it anyway is legal as long as it agrees; a mismatch is a validation error that names both values.

There is one situation today where writing it is not merely legal but necessary. Cross-dialect translation reads the dialect from the upstream config rather than from the compiled descriptor, and the descriptor path leaves that field empty. If you are enabling cross-dialect translation, name both provider: and dialect: on the target upstream. The cross-dialect page shows what happens when you do not, with both captures.