Tools and function calling
Give the model functions to call using the standard OpenAI tools and tool_calls flow through FluxRouter.
Tool calling (also called function calling) lets the model ask your code to run a function and feed the result back into the conversation. FluxRouter speaks the OpenAI wire format, so you use the standard tools and tool_calls flow against https://api.fluxrouter.ai/v1/chat/completions. Nothing about the request is Flux-specific except the base URL and the flux-auto model.
How the flow works
- You send the conversation plus a
toolsarray describing the functions the model is allowed to call. - If the model decides to call a function, it responds with
tool_callsinstead of a final answer. Each tool call has anid, a functionname, and JSONarguments. - Your code runs the function and appends a message with
role: "tool", the matchingtool_call_id, and the function's result. - You send the conversation back. The model uses the tool result to produce its final answer.
Minimal example
This example gives the model one tool, get_weather, and handles the round trip.
import json
from openai import OpenAI
client = OpenAI(
api_key="sk-...", # your Flux key
base_url="https://api.fluxrouter.ai/v1", # the one line you change
)
tools = [
{
"type": "function",
"function": {
"name": "get_weather",
"description": "Get the current weather for a city.",
"parameters": {
"type": "object",
"properties": {
"city": {"type": "string", "description": "City name"}
},
"required": ["city"],
},
},
}
]
messages = [{"role": "user", "content": "What's the weather in Lisbon?"}]
# 1. First call: the model decides whether to use the tool.
first = client.chat.completions.create(
model="flux-auto",
messages=messages,
tools=tools,
)
choice = first.choices[0].message
messages.append(choice)
# 2. Run any tool calls the model requested.
if choice.tool_calls:
for call in choice.tool_calls:
args = json.loads(call.function.arguments)
result = {"city": args["city"], "temp_c": 21, "sky": "clear"} # your real function here
messages.append(
{
"role": "tool",
"tool_call_id": call.id,
"content": json.dumps(result),
}
)
# 3. Second call: the model answers using the tool result.
final = client.chat.completions.create(
model="flux-auto",
messages=messages,
tools=tools,
)
print(final.choices[0].message.content)
else:
print(choice.content)
curl (single turn)
curl https://api.fluxrouter.ai/v1/chat/completions \
-H "Authorization: Bearer $FLUX_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "flux-auto",
"messages": [{ "role": "user", "content": "What is the weather in Lisbon?" }],
"tools": [
{
"type": "function",
"function": {
"name": "get_weather",
"description": "Get the current weather for a city.",
"parameters": {
"type": "object",
"properties": { "city": { "type": "string" } },
"required": ["city"]
}
}
}
]
}'
Forcing or disabling tool use
The standard OpenAI tool_choice field works as usual:
"tool_choice": "auto"(default) lets the model decide."tool_choice": "none"forbids tool use for this turn."tool_choice": {"type": "function", "function": {"name": "get_weather"}}forces a specific tool.
Make sure your model supports tools
Tool calling depends on the model that serves the request. flux-auto routes to a sensible model, and most general-purpose models in the Flux catalog support tools, but support is a property of the underlying model, not of FluxRouter.
If your application always needs tool calling, pin a tool-capable model instead of relying on the router. Pass a flux-pinned-* id (for example flux-pinned-claude-sonnet or flux-pinned-gpt-5) so every request lands on a model you have verified supports tools. See Models for the full list of pinned aliases.
Anthropic shape
If you call the Anthropic-compatible base at https://api.fluxrouter.ai/anthropic, use Anthropic's native tools and tool_use / tool_result blocks exactly as you would calling Anthropic directly. The mechanics differ by wire format, but the round trip is the same: the model requests a tool, you run it, you send the result back.