> ## Documentation Index
> Fetch the complete documentation index at: https://docs.anyone.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# POST /v1/messages — Anthropic Claude Messages format

> Use Anthropic's native Messages API format to interact with Claude models through Anyone. Authenticate with x-api-key and anthropic-version headers.

The `/v1/messages` endpoint accepts requests in Anthropic's native Claude Messages API format. If you already use the `anthropic` Python or JavaScript SDK, you can redirect it at Anyone by changing only the base URL — all request and response fields remain identical. Anyone authenticates you with the API key from your dashboard and routes the request to the configured Claude channel. You can also send Claude-format requests to non-Claude upstream channels; Anyone translates the format automatically where possible.

## Endpoint

```
POST /v1/messages
```

## Authentication

Claude Messages requests use two headers instead of `Authorization`:

| Header              | Required | Description          |
| ------------------- | -------- | -------------------- |
| `x-api-key`         | Yes      | Your Anyone API key  |
| `anthropic-version` | Yes      | Must be `2023-06-01` |

<Note>
  You may alternatively use `Authorization: Bearer YOUR_TOKEN` for the API key if your client does not support `x-api-key`. Anyone accepts both forms.
</Note>

## Request parameters

<ParamField body="model" type="string" required>
  The Claude model to use, for example `claude-opus-4-6` or `claude-sonnet-4-6`. To enable extended thinking, use the `-thinking` model name suffix: `claude-sonnet-4-6-thinking`.
</ParamField>

<ParamField body="messages" type="object[]" required>
  The conversation history. Messages alternate between `user` and `assistant` roles. The first message must have role `user`.

  <Expandable title="message properties">
    <ParamField body="messages[].role" type="string" required>
      The message author role. One of `"user"` or `"assistant"`.
    </ParamField>

    <ParamField body="messages[].content" type="string | object[]" required>
      The message content. Pass a plain string for text, or an array of content blocks for multimodal input.

      Each content block is an object with a `type` field. Supported types:

      * `"text"` — a text block with a `text` field
      * `"image"` — an image block with a `source` object containing `type` (`"base64"` or `"url"`), `media_type`, and `data` or `url`
      * `"tool_use"` — a model-generated tool call with `id`, `name`, and `input`
      * `"tool_result"` — the result of a tool call with `tool_use_id` and `content`
    </ParamField>
  </Expandable>
</ParamField>

<ParamField body="max_tokens" type="integer" required>
  The maximum number of tokens to generate. This field is required by the Claude Messages API. For Claude models, the value must not exceed the model's output token limit.
</ParamField>

<ParamField body="system" type="string | object[]">
  A system prompt that sets context and instructions for the conversation. Pass a plain string, or an array of content blocks for advanced use cases such as caching system prompts.
</ParamField>

<ParamField body="stream" type="boolean" default="false">
  When `true`, the response is returned as a stream of server-sent events using Anthropic's streaming format. Events include `message_start`, `content_block_start`, `content_block_delta`, `content_block_stop`, `message_delta`, and `message_stop`.
</ParamField>

<ParamField body="temperature" type="number">
  Sampling temperature between `0` and `1`. Higher values produce more varied output.
</ParamField>

<ParamField body="top_p" type="number">
  Nucleus sampling probability mass between `0` and `1`. Recommended when `temperature` is not set.
</ParamField>

<ParamField body="top_k" type="integer">
  Sample from only the top `k` most likely tokens. Not recommended for most use cases.
</ParamField>

<ParamField body="stop_sequences" type="string[]">
  Custom sequences at which the model will stop generating. The stop sequence itself is not included in the output.
</ParamField>

<ParamField body="tools" type="object[]">
  Tools the model may call. Each tool defines a function the model can invoke.

  <Expandable title="tool properties">
    <ParamField body="tools[].name" type="string" required>
      The name of the tool. Must match the pattern `^[a-zA-Z0-9_-]{1,64}$`.
    </ParamField>

    <ParamField body="tools[].description" type="string">
      A description of what the tool does. The model uses this to decide when to call it.
    </ParamField>

    <ParamField body="tools[].input_schema" type="object" required>
      The tool's input parameters in JSON Schema format. Must have `type: "object"` at the top level, with a `properties` map and optional `required` array.
    </ParamField>
  </Expandable>
</ParamField>

<ParamField body="tool_choice" type="object">
  Controls how the model selects tools.

  <Expandable title="tool_choice properties">
    <ParamField body="tool_choice.type" type="string" required>
      One of `"auto"` (model decides), `"any"` (must call a tool), or `"tool"` (must call a specific tool).
    </ParamField>

    <ParamField body="tool_choice.name" type="string">
      Required when `type` is `"tool"`. The name of the tool to call.
    </ParamField>

    <ParamField body="tool_choice.disable_parallel_tool_use" type="boolean" default="false">
      When `true`, the model may only call one tool at a time.
    </ParamField>
  </Expandable>
</ParamField>

<ParamField body="thinking" type="object">
  Enable extended thinking for supported models. Use the `-thinking` model name suffix as an alternative.

  <Expandable title="thinking properties">
    <ParamField body="thinking.type" type="string" required>
      Must be `"enabled"`.
    </ParamField>

    <ParamField body="thinking.budget_tokens" type="integer">
      The maximum number of tokens the model may use for internal reasoning before producing its response.
    </ParamField>
  </Expandable>
</ParamField>

## Response fields

<ResponseField name="id" type="string">
  A unique identifier for this message in the format `msg_...`.
</ResponseField>

<ResponseField name="type" type="string">
  Always `"message"` for complete responses.
</ResponseField>

<ResponseField name="role" type="string">
  Always `"assistant"` for generated messages.
</ResponseField>

<ResponseField name="content" type="object[]">
  An array of content blocks in the response.

  <Expandable title="content block properties">
    <ResponseField name="content[].type" type="string">
      The block type: `"text"` for text output, `"tool_use"` when the model calls a tool, or `"thinking"` for extended thinking content.
    </ResponseField>

    <ResponseField name="content[].text" type="string">
      The text content. Present when `type` is `"text"`.
    </ResponseField>

    <ResponseField name="content[].id" type="string">
      The tool call ID. Present when `type` is `"tool_use"`.
    </ResponseField>

    <ResponseField name="content[].name" type="string">
      The tool name. Present when `type` is `"tool_use"`.
    </ResponseField>

    <ResponseField name="content[].input" type="object">
      The tool call arguments. Present when `type` is `"tool_use"`.
    </ResponseField>

    <ResponseField name="content[].thinking" type="string">
      The model's reasoning content. Present when `type` is `"thinking"` and extended thinking is enabled.
    </ResponseField>
  </Expandable>
</ResponseField>

<ResponseField name="model" type="string">
  The model that generated the response.
</ResponseField>

<ResponseField name="stop_reason" type="string">
  Why the model stopped generating. One of `"end_turn"` (natural end), `"max_tokens"` (token limit reached), `"stop_sequence"` (custom stop sequence matched), or `"tool_use"` (model called a tool).
</ResponseField>

<ResponseField name="usage" type="object">
  Token counts for this request.

  <Expandable title="usage properties">
    <ResponseField name="usage.input_tokens" type="integer">
      Number of tokens in the input messages and system prompt.
    </ResponseField>

    <ResponseField name="usage.output_tokens" type="integer">
      Number of tokens in the generated response.
    </ResponseField>

    <ResponseField name="usage.cache_creation_input_tokens" type="integer">
      Tokens written to the prompt cache, if prompt caching was used.
    </ResponseField>

    <ResponseField name="usage.cache_read_input_tokens" type="integer">
      Tokens read from the prompt cache, if prompt caching was used.
    </ResponseField>
  </Expandable>
</ResponseField>

## Examples

<Tabs>
  <Tab title="Non-streaming">
    <CodeGroup>
      ```bash cURL theme={null}
      curl https://api.anyone.ai/v1/messages \
        -H "x-api-key: YOUR_TOKEN" \
        -H "anthropic-version: 2023-06-01" \
        -H "Content-Type: application/json" \
        -d '{
          "model": "claude-opus-4-6",
          "max_tokens": 1024,
          "system": "You are a concise technical assistant.",
          "messages": [
            {"role": "user", "content": "Explain what a mutex is in one paragraph."}
          ]
        }'
      ```

      ```python Python (anthropic SDK) theme={null}
      import anthropic

      client = anthropic.Anthropic(
          api_key="YOUR_TOKEN",
          base_url="https://api.anyone.ai",
      )

      message = client.messages.create(
          model="claude-opus-4-6",
          max_tokens=1024,
          system="You are a concise technical assistant.",
          messages=[
              {"role": "user", "content": "Explain what a mutex is in one paragraph."}
          ],
      )

      print(message.content[0].text)
      ```

      ```javascript JavaScript (anthropic SDK) theme={null}
      import Anthropic from "@anthropic-ai/sdk";

      const client = new Anthropic({
        apiKey: "YOUR_TOKEN",
        baseURL: "https://api.anyone.ai",
      });

      const message = await client.messages.create({
        model: "claude-opus-4-6",
        max_tokens: 1024,
        system: "You are a concise technical assistant.",
        messages: [
          { role: "user", content: "Explain what a mutex is in one paragraph." },
        ],
      });

      console.log(message.content[0].text);
      ```
    </CodeGroup>

    **Example response:**

    ```json theme={null}
    {
      "id": "msg_01XFDUDYJgAACzvnptvVoYEL",
      "type": "message",
      "role": "assistant",
      "content": [
        {
          "type": "text",
          "text": "A mutex (mutual exclusion lock) is a synchronization primitive that ensures only one thread can access a shared resource at a time..."
        }
      ],
      "model": "claude-opus-4-6",
      "stop_reason": "end_turn",
      "usage": {
        "input_tokens": 28,
        "output_tokens": 87,
        "cache_creation_input_tokens": 0,
        "cache_read_input_tokens": 0
      }
    }
    ```
  </Tab>

  <Tab title="Streaming">
    ```bash cURL theme={null}
    curl https://api.anyone.ai/v1/messages \
      -H "x-api-key: YOUR_TOKEN" \
      -H "anthropic-version: 2023-06-01" \
      -H "Content-Type: application/json" \
      -d '{
        "model": "claude-opus-4-6",
        "max_tokens": 512,
        "stream": true,
        "messages": [
          {"role": "user", "content": "Write a haiku about databases."}
        ]
      }'
    ```

    The server sends events in Anthropic's streaming format:

    ```
    event: message_start
    data: {"type":"message_start","message":{"id":"msg_01abc","type":"message","role":"assistant","content":[],"model":"claude-opus-4-6","stop_reason":null,"usage":{"input_tokens":14,"output_tokens":0}}}

    event: content_block_start
    data: {"type":"content_block_start","index":0,"content_block":{"type":"text","text":""}}

    event: content_block_delta
    data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":"Rows"}}

    event: message_stop
    data: {"type":"message_stop"}
    ```
  </Tab>

  <Tab title="Tool use">
    ```bash cURL theme={null}
    curl https://api.anyone.ai/v1/messages \
      -H "x-api-key: YOUR_TOKEN" \
      -H "anthropic-version: 2023-06-01" \
      -H "Content-Type: application/json" \
      -d '{
        "model": "claude-opus-4-6",
        "max_tokens": 1024,
        "tools": [
          {
            "name": "get_weather",
            "description": "Get the current weather for a location.",
            "input_schema": {
              "type": "object",
              "properties": {
                "location": {
                  "type": "string",
                  "description": "City name, e.g. San Francisco"
                }
              },
              "required": ["location"]
            }
          }
        ],
        "messages": [
          {"role": "user", "content": "What is the weather in Tokyo?"}
        ]
      }'
    ```
  </Tab>
</Tabs>

## Format conversion

You can also route Claude-format requests (`/v1/messages`) to non-Claude upstream channels. Anyone performs automatic format conversion, translating the Claude Messages format to the upstream provider's native format. This lets you use a single client format across providers. Conversion is best-effort; some Claude-specific features (such as extended thinking) may not be available on all upstream channels.
