Build
Make a request
Send a chat completion to SID-1 and read the tool calls it returns.


This guide covers how to make a single request to SID-1 and parse the response. SID-1 uses the tool-calling API: all actions are defined as tools and in response to every request, SID-1 will return a list of tool calls that you need to parse. The assistant message's content carries the model's reasoning, not an answer: ignore it, and never show it to end users.
Send the request
SID-1 uses an OpenAI-compatible v1/chat/completions endpoint. You're free to use any package compatible with that API like the official OpenAI package, LangChain ChatOpenAI, or Vercel's AI SDK. SID-1 takes a system prompt that includes a list of tools describing the search queries your backend supports. It then returns a list of these tool invocations.
Here's everything you need to do:
- Set the base URL to
https://api.sid-1.com/v1and set aSID_API_KEY. Create a key on the API keys page. - Define a system prompt according to the system prompt specs. Tool parameters and descriptions go into the system prompt.
- Pass a
toolslist to activate tool calling. You must include at least one entry, but SID-1 ignores its contents, so a single placeholder stub is enough. The real tools live in the system prompt. See the tool reference for details. - Place the query, and only the query, in the first user message. Multiple queries should be separated into multiple requests. Extra information or instructions should go in the system prompt.
- Use
sid-1as the model name.
This example request sends one question and passes a single placeholder tool to switch on tool-call parsing. The real tools (search, text_search, read, and report_helpful_ids) are described in the system prompt, so SID-1 reads each tool's behavior from there and returns tool calls for your code to run. report_helpful_ids has a special purpose that we'll cover in Loop and exit.
# SYSTEM_PROMPT contains the system prompt from /docs/reference/system-prompt.
curl https://api.sid-1.com/v1/chat/completions \
-H "Authorization: Bearer $SID_API_KEY" \
-H "Content-Type: application/json" \
-d @- <<JSON
{
"model": "sid-1",
"messages": [
{"role": "system", "content": $(jq -Rs . <<< "$SYSTEM_PROMPT")},
{"role": "user", "content": "In which cities were the indoor and outdoor 4 minute mile records set?"}
],
"tools": [
{"type": "function", "function": {"name": "dummy"}}
]
}
JSONimport os
from openai import OpenAI
client = OpenAI(base_url="https://api.sid-1.com/v1", api_key=os.environ["SID_API_KEY"])
# SYSTEM_PROMPT contains the system prompt. tools contains a single placeholder stub.
messages = [
{"role": "system", "content": SYSTEM_PROMPT},
{"role": "user", "content": "In which cities were the indoor and outdoor 4 minute mile records set?"},
]
response = client.chat.completions.create(model="sid-1", messages=messages, tools=tools)
assistant_msg = response.choices[0].messageimport OpenAI from "openai";
const client = new OpenAI({ baseURL: "https://api.sid-1.com/v1", apiKey: process.env.SID_API_KEY });
// SYSTEM_PROMPT contains the system prompt. tools contains a single placeholder stub.
const messages: OpenAI.Chat.Completions.ChatCompletionMessageParam[] = [
{ role: "system", content: SYSTEM_PROMPT },
{ role: "user", content: "In which cities were the indoor and outdoor 4 minute mile records set?" },
];
const response = await client.chat.completions.create({ model: "sid-1", messages, tools });
const assistantMsg = response.choices[0].message;tool_choice: required is not supported
The chat completions API for SID-1 currently does not support setting the parameter "tool_choice": "required". Either omit the parameter or set it explicitly to the default, "tool_choice": "auto".
List tool names only
The tools array tells the API which functions SID-1 can call. Put each tool's behavior and arguments in the system prompt, not in tools. SID-1 does not read description or parameters fields from this request.
Read the response
SID-1 returns tool calls in the assistant message's tool_calls array. A turn can (and will) include more than one call, so iterate over the full array and run the calls in parallel (see run tool calls in parallel). Each entry has a tool name and an arguments string of JSON.
{
"role": "assistant",
"content": "<think>\nI need the cities for both records, so I'll run a few searches in parallel and a lexical search for the exact phrase.\n</think>\n\n",
"tool_calls": [
{
"id": "chatcmpl-tool-1a2b3c4d",
"type": "function",
"function": {
"name": "search",
"arguments": "{\"query\": \"indoor 4 minute mile record city\", \"limit\": 5}"
}
},
{
"id": "chatcmpl-tool-5e6f7a8b",
"type": "function",
"function": {
"name": "search",
"arguments": "{\"query\": \"outdoor 4 minute mile record city\", \"limit\": 5}"
}
},
{
"id": "chatcmpl-tool-9c0d1e2f",
"type": "function",
"function": {
"name": "text_search",
"arguments": "{\"query\": \"four-minute mile world record\", \"limit\": 10}"
}
}
]
}Ignore content, read only tool_calls
The assistant message's content holds the model's internal reasoning (returned in redacted_thinking tags), not a user-facing answer. Parse only tool_calls, and never show content to end users. limit is optional (default 5); the model sets it per call and may omit it.
Loop over every entry, extract the name, and parse the arguments JSON string before you dispatch to your handler. We cover the handlers in more depth in the next section. For now, we print each tool call to the console:
import json
for tc in assistant_msg.tool_calls:
name = tc.function.name
# arguments is a JSON string, so parse it before passing it to your handler.
arguments = json.loads(tc.function.arguments)
print(name, arguments)for (const tc of assistantMsg.tool_calls ?? []) {
const name = tc.function.name;
// arguments is a JSON string, so parse it before passing it to your handler.
const args = JSON.parse(tc.function.arguments);
console.log(name, args);
}When there's no tool call
Treat a response without tool calls as a failed turn. Retry the request (preferred) or end the run instead of passing the message back into the loop. If this happens often, double-check your tool definitions and system prompt.
if not assistant_msg.tool_calls:
raise RuntimeError("Expected SID-1 to return at least one tool call.")if (!assistantMsg.tool_calls?.length) {
throw new Error("Expected SID-1 to return at least one tool call.");
}