Skip to content
Relaykit
DocsResponses API

Build

Responses API

Use OpenAI's Responses API through the gateway. Which models support it, why requests should be stateless, and when chat completions is the better choice.

Updated View .md
On this page

POST /v1/responses is OpenAI’s newer request format: input instead of messages, typed output items, and built-in reasoning controls. OpenAI’s Codex CLI and some agent frameworks use it by default.

POST https://api.oneaiapikey.com/v1/responses (OpenAI format)

Which models

Family /v1/responses
GPT Supported. This is OpenAI’s own format.
Claude Supported. The gateway translates the request to Anthropic’s format. Stateful fields are rejected (see below).
Others Depends on the provider’s own Responses support. Use chat completions for these models; it works for every model.

If you are writing new code and do not need a Responses-only feature, chat completions is the safer choice: one format, every model.

Send a request

curl https://api.oneaiapikey.com/v1/responses \
  -H "Authorization: Bearer $RELAYKIT_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "gpt-5.6-terra",
    "instructions": "Answer in one short paragraph.",
    "input": "What does idempotent mean for an HTTP method?",
    "max_output_tokens": 400,
    "store": false
  }'
import os
from openai import OpenAI

client = OpenAI(base_url="https://api.oneaiapikey.com/v1", api_key=os.environ["RELAYKIT_API_KEY"])

response = client.responses.create(
    model="gpt-5.6-terra",
    instructions="Answer in one short paragraph.",
    input="What does idempotent mean for an HTTP method?",
    max_output_tokens=400,
    store=False,
)
print(response.output_text)
print(response.usage)
import OpenAI from "openai";

const client = new OpenAI({ baseURL: "https://api.oneaiapikey.com/v1", apiKey: process.env.RELAYKIT_API_KEY });

const response = await client.responses.create({
  model: "gpt-5.6-terra",
  instructions: "Answer in one short paragraph.",
  input: "What does idempotent mean for an HTTP method?",
  max_output_tokens: 400,
  store: false,
});
console.log(response.output_text);
console.log(response.usage);

The reply has an output array of items (message, reasoning, function_call …). The SDKs’ output_text joins the text for you. usage has input_tokens, output_tokens and their details (cached and reasoning tokens).

Keep requests stateless

The gateway does not store responses. Send the whole conversation in input each time, set store: false, and do not rely on server-side state:

  • previous_response_id, conversation and stored prompt templates are not supported. For Claude models, a request that uses them is rejected with an error.
  • GET /v1/responses/{id} and DELETE /v1/responses/{id} are not available. Keep anything you need from a response yourself.
  • Background mode (background: true) is of no use here, because its result can only be fetched with GET /v1/responses/{id}.
Multi-turn without stored state
history = [
    {"role": "user", "content": "Name a sorting algorithm with O(n log n) worst case."},
]
first = client.responses.create(model="gpt-5.6-terra", input=history, store=False)

# Append the model's output items, then the next user turn, and send everything again.
history += [item.model_dump(exclude_none=True) for item in first.output]
history.append({"role": "user", "content": "How much extra memory does it need?"})
second = client.responses.create(model="gpt-5.6-terra", input=history, store=False)
print(second.output_text)

Streaming and tools

  • stream: true returns Responses-style server-sent events (response.created, response.output_text.delta, …, response.completed). The final response.completed event carries usage.
  • Function tools ("type": "function") work as in OpenAI’s API. Provider-hosted tools such as file search or code interpreter only work where the provider runs them, and the gateway does not host files for them.
  • reasoning: {"effort": "low" | "medium" | "high"} sets the thinking effort on reasoning models. See Reasoning models.

↑ ↓ moveEnter openEsc close