Model and routing
Send one of the supported model IDs below as themodel. each::labs routes the
request through the LLM Router to OpenRouter.
You call a single each::labs endpoint; provider selection and credentials stay on
our side, and usage is billed to your each::labs account.
Unlike chat completions, this is not an OpenAI-compatible operation and has no
corresponding OpenAI SDK method. Call it directly over HTTP.
Supported models
The list of decision models changes as models are added or retired, so read it from the API instead of hard-coding it:id in the response is accepted as model. Use it exactly as returned.
The examples below use typesafe/jev-1.13; replace it with another listed ID to
select that model.
Endpoint
Authentication
Pass a standard API key as a Bearer token:Request body
The body takesmodel, state, questions, and an optional images field.
Any other field is rejected.
Each question is an object with a
type, instructions, and — depending on the
type — criteria:
instructions and every criteria value accept a string, an object, or an
array. The response preserves your question names as the keys of answers.
Images
Models that read images also evaluate images sent with the request. Pass them inimages. Each entry can be an image URL, a base64 data URL, or plain base64:
state array as image_url items; text
items are plain strings:
url can be an image URL, a base64 data URL, or plain base64. each::labs
also accepts these shapes and converts them before calling the model:
-
A Responses-style part:
{ "type": "input_image", "image_url": "https://..." }. -
image_urlgiven as a plain string instead of an object. -
An image part nested inside an object, such as
"state": { "photo": { "type": "image_url", ... } }. The image moves to its ownstateitem, and[image 1]is left in its place so your text can still refer to it. -
Send
stateas a JSON array, not as a string that contains JSON. A string is read as text, so the model never sees the image and the base64 is billed as input tokens. Such a request returns400. -
Images must be PNG, JPEG, or WebP. Send up to 16 images per request, each under
5 MB and 12 MB in total. A URL must be public
httporhttps. -
Only some decision models read images, for example
cloudflare/clef,cloudflare/clef-flash,typesafe/jev-1.13, andliquid/d1. A text-only model reads the image as text. Model limits also apply: Clef works best with images under about 300 KB. Jev accepts PNG and JPEG with each side between 256 and 1568 px and 78,400 to 2,458,624 px in total; smaller images return400.
Example
Response
Answer fields
Every answer carries the question’stype. The remaining fields depend on it:
Usage
When the upstream returns a decision
id, it is included in the response.
Run as a model
Decisions is also available as theeachlabs-decisions model, so you can run it
like any other each::labs model: through POST /v1/prediction, in the
playground, and as a step in a workflow. The input takes the same model,
state, questions, and images fields as the request body above. In the
playground, upload files in the Images field.
GET /v1/prediction/{id}, or pass a
webhook_url, until status is success. The output has the same answers,
model, and usage fields as a direct response:
input.model returns 400 with a message naming the ID.
In a workflow
Add aneachlabs-decisions model step, then branch on or pass along its answers
with a $. reference to
$.<step_id>.primary.answers.<question>:
$.decide.primary.answers.color.choice.