Skip to main content
POST /v1/messages Tools are declared with a flat input_schema (no outer type: "function" wrapper). The model returns tool_use content blocks.

Define a tool

tools = [{
    "name": "get_weather",
    "description": "Get the weather for a city",
    "input_schema": {
        "type": "object",
        "properties": {"city": {"type": "string"}},
        "required": ["city"],
    },
}]

Full loop

from anthropic import Anthropic

client = Anthropic(base_url="https://api.abliteration.ai", auth_token=os.environ["ABLIT_KEY"])

messages = [{"role": "user", "content": "What's the weather in Lagos?"}]

resp = client.messages.create(
    model="abliterated-model",
    max_tokens=1024,
    tools=tools,
    messages=messages,
)

messages.append({"role": "assistant", "content": resp.content})

tool_results = []
for block in resp.content:
    if block.type == "tool_use":
        result = get_weather(block.input["city"])  # your function
        tool_results.append({
            "type": "tool_result",
            "tool_use_id": block.id,
            "content": str(result),
        })

messages.append({"role": "user", "content": tool_results})

final = client.messages.create(
    model="abliterated-model",
    max_tokens=1024,
    tools=tools,
    messages=messages,
)
print(final.content[0].text)

Streaming

Stream with stream=True. Tool-use blocks arrive as content_block_start with type: "tool_use", followed by input_json_delta events. stop_reason: "tool_use" signals the turn needs a follow-up with tool_result.

Forcing a tool

tool_choice={"type": "tool", "name": "get_weather"}
{type: "any"} forces some tool; {type: "auto"} is the default.

Parallel tool calls

Multiple tool_use blocks can appear in the same response. Return one tool_result block per tool_use_id in the next user turn.