Вот несколько примеров кода, демонстрирующих различные шаблоны и методы использования инструментов. Для краткости инструменты являются простыми, а описания инструментов короче, чем было бы идеально для обеспечения наилучшей производительности. Смотрите указание инструментов для получения дополнительной информации.

Один инструмент

Этот пример показывает базовую ситуацию с одним инструментом, используя инструмент get_weather.

curl https://api.anthropic.com/v1/messages \
     --header "x-api-key: $ANTHROPIC_API_KEY" \
     --header "anthropic-version: 2023-06-01" \
     --header "content-type: application/json" \
     --data \
'{
    "model": "claude-3-opus-20240229",
    "max_tokens": 1024,
    "tools": [{
        "name": "get_weather",
        "description": "Получить текущую погоду в заданном месте",
        "input_schema": {
            "type": "object",
            "properties": {
                "location": {
                    "type": "string",
                    "description": "Город и штат, например San Francisco, CA"
                },
                "unit": {
                    "type": "string",
                    "enum": ["celsius", "fahrenheit"],
                    "description": "Единица измерения температуры, либо \"celsius\", либо \"fahrenheit\""
                }
            },
            "required": ["location"]
        }
    }],
    "messages": [{"role": "user", "content": "Какая погода в Сан-Франциско?"}]
}'

Claude вернет ответ, подобный этому:

JSON
{
  "id": "msg_01Aq9w938a90dw8q",
  "model": "claude-3-opus-20240229",
  "stop_reason": "tool_use",
  "role": "assistant",
  "content": [
    {
      "type": "text",
      "text": "<thinking>Мне нужно вызвать функцию get_weather, и пользователь хочет SF, что, вероятно, означает Сан-Франциско, Калифорния.</thinking>"
    },
    {
      "type": "tool_use",
      "id": "toolu_01A09q90qw90lq917835lq9", 
      "name": "get_weather",
      "input": {"location": "San Francisco, CA", "unit": "celsius"}
    }
  ]
}

Затем вам нужно будет выполнить функцию get_weather с предоставленными входными данными и вернуть результат в новом сообщении user:

curl https://api.anthropic.com/v1/messages \
     --header "x-api-key: $ANTHROPIC_API_KEY" \
     --header "anthropic-version: 2023-06-01" \
     --header "content-type: application/json" \
     --data \
'{
    "model": "claude-3-opus-20240229",
    "max_tokens": 1024,
    "tools": [
        {
            "name": "get_weather",
            "description": "Получить текущую погоду в заданном месте",
            "input_schema": {
                "type": "object",
                "properties": {
                    "location": {
                        "type": "string",
                        "description": "Город и штат, например San Francisco, CA"
                    },
                    "unit": {
                        "type": "string",
                        "enum": ["celsius", "fahrenheit"],
                        "description": "Единица измерения температуры, либо \"celsius\", либо \"fahrenheit\""
                    }
                },
                "required": ["location"]
            }
        }
    ],
    "messages": [
        {
            "role": "user",
            "content": "Какая погода в Сан-Франциско?"
        },
        {
            "role": "assistant",
            "content": [
                {
                    "type": "text",
                    "text": "<thinking>Мне нужно использовать get_weather, и пользователь хочет SF, что, вероятно, означает Сан-Франциско, Калифорния.</thinking>"
                },
                {
                    "type": "tool_use",
                    "id": "toolu_01A09q90qw90lq917835lq9",
                    "name": "get_weather",
                    "input": {
                        "location": "San Francisco, CA",
                        "unit": "celsius"
                    }
                }
            ]
        },
        {
            "role": "user",
            "content": [
                {
                    "type": "tool_result",
                    "tool_use_id": "toolu_01A09q90qw90lq917835lq9",
                    "content": "15 градусов"
                }
            ]
        }
    ]
}'

Это выведет окончательный ответ Claude с учетом данных о погоде:

JSON
{
  "id": "msg_01Aq9w938a90dw8q",
  "model": "claude-3-opus-20240229",
  "stop_reason": "stop_sequence",
  "role": "assistant",
  "content": [
    {
      "type": "text",
      "text": "Текущая погода в Сан-Франциско 15 градусов Цельсия (59 градусов по Фаренгейту). Прохладный день в городе у залива!"
    }
  ]
}

Недостающая информация

Если запрос пользователя не содержит достаточно информации для заполнения всех необходимых параметров инструмента, Claude 3 Opus с гораздо большей вероятностью распознает, что параметр отсутствует, и запросит его. Claude 3 Sonnet может спросить, особенно когда его просят подумать перед выводом запроса инструмента. Но он также может сделать все возможное, чтобы вывести разумное значение.

Например, используя инструмент get_weather выше, если вы спросите Claude “Какая погода?” без указания местоположения, Claude, особенно Claude 3 Sonnet, может сделать предположение о входных данных инструментов:

JSON
{
  "type": "tool_use",
  "id": "toolu_01A09q90qw90lq917835lq9",
  "name": "get_weather", 
  "input": {"location": "New York, NY", "unit": "fahrenheit"}
}

Такое поведение не гарантируется, особенно для более неоднозначных запросов и для моделей менее интеллектуальных, чем Claude 3 Opus. Если у Claude 3 Opus недостаточно контекста для заполнения необходимых параметров, он с гораздо большей вероятностью ответит уточняющим вопросом вместо вызова инструмента.


Несколько инструментов

Вы можете предоставить Claude несколько инструментов на выбор в одном запросе. Вот пример с инструментами get_weather и get_time, а также пользовательским запросом, который требует обоих.

curl https://api.anthropic.com/v1/messages \
     --header "x-api-key: $ANTHROPIC_API_KEY" \
     --header "anthropic-version: 2023-06-01" \
     --header "content-type: application/json" \
     --data \
'{
    "model": "claude-3-opus-20240229",
    "max_tokens": 1024,
    "tools": [{
        "name": "get_weather",
        "description": "Получить текущую погоду в заданном месте",
        "input_schema": {
            "type": "object",
            "properties": {
                "location": {
                    "type": "string",
                    "description": "Город и штат, например San Francisco, CA"
                },
                "unit": {
                    "type": "string",
                    "enum": ["celsius", "fahrenheit"],
                    "description": "Единица измерения температуры, либо 'celsius', либо 'fahrenheit'"
                }
            },
            "required": ["location"]
        }
    },
    {
        "name": "get_time",
        "description": "Получить текущее время в заданном часовом поясе",
        "input_schema": {
            "type": "object",
            "properties": {
                "timezone": {
                    "type": "string",
                    "description": "Название часового пояса IANA, например America/Los_Angeles"
                }
            },
            "required": ["timezone"]
        }
    }],
    "messages": [{
        "role": "user",
        "content": "Какая сейчас погода в Нью-Йорке? И который там час?"
    }]
}'

В этом случае Claude, скорее всего, попытается использовать два отдельных инструмента, по одному за раз — get_weather, а затем get_time — чтобы полностью ответить на вопрос пользователя. Однако он также иногда может выводить два блока tool_use одновременно, особенно если они не зависят друг от друга. Вам нужно будет выполнить каждый инструмент и вернуть их результаты в отдельных блоках tool_result в одном сообщении user.


Последовательные инструменты

Некоторые задачи могут потребовать вызова нескольких инструментов последовательно, используя вывод одного инстру мента в качестве входных данных для другого. В таком случае Claude будет вызывать по одному инструменту за раз. Если его попросить вызвать все инструменты сразу, Claude, вероятно, будет угадывать параметры для инструментов, расположенных дальше по цепочке, если они зависят от результатов инструментов, расположенных выше по цепочке.

Вот пример использования инструмента get_location для получения местоположения пользователя, а затем передачи этого местоположения в инструмент get_weather:

curl https://api.anthropic.com/v1/messages \
     --header "x-api-key: $ANTHROPIC_API_KEY" \
     --header "anthropic-version: 2023-06-01" \
     --header "content-type: application/json" \
     --data \
'{
    "model": "claude-3-opus-20240229",
    "max_tokens": 1024,
    "tools": [
        {
            "name": "get_location",
            "description": "Получить текущее местоположение пользователя на основе его IP-адреса. Этот инструмент не имеет параметров или аргументов.",
            "input_schema": {
                "type": "object",
                "properties": {}
            }
        },
        {
            "name": "get_weather",
            "description": "Получить текущую погоду в заданном месте",
            "input_schema": {
                "type": "object",
                "properties": {
                    "location": {
                        "type": "string",
                        "description": "Город и штат, например San Francisco, CA"
                    },
                    "unit": {
                        "type": "string",
                        "enum": ["celsius", "fahrenheit"],
                        "description": "Единица измерения температуры, либо 'celsius', либо 'fahrenheit'"
                    }
                },
                "required": ["location"]
            }
        }
    ],
    "messages": [{
        "role": "user",
        "content": "Какая погода там, где я нахожусь?"
    }]
}'

В этом случае Claude сначала вызовет инструмент get_location, чтобы получить местоположение пользователя. После того, как вы вернете местоположение в tool_result, Claude затем вызовет get_weather с этим местоположением, чтобы получить окончательный ответ.

Полный разговор может выглядеть так:

РольСодержание
ПользовательКакая погода там, где я нахожусь?
Ассистент<thinking>Чтобы ответить на это, мне сначала нужно определить местоположение пользователя с помощью инструмента get_location. Затем я могу передать это местоположение в инструмент get_weather, чтобы узнать текущую погоду там.</thinking>[Использование инструмента для get_location]
Пользователь[Результат инструмента для get_location с соответствующим идентификатором и результатом San Francisco, CA]
Ассистент[Использование инструмента для get_weather со следующими входными данными]{ “location”: “San Francisco, CA”, “unit”: “fahrenheit” }
Пользователь[Результат инструмента для get_weather с соответствующим идентификатором и результатом “59°F (15°C), в основном облачно”]
АссистентИсходя из вашего текущего местоположения в Сан-Франциско, Калифорния, погода сейчас 59°F (15°C) и в основном облачно. Довольно прохладный и пасмурный день в городе. Возможно, вам стоит взять с собой легкую куртку, если вы собираетесь на улицу.

Этот пример демонстрирует, как Claude может связать несколько вызовов инструментов для ответа на вопрос, требующий сбора данных из разных источников. Основные шаги:

  1. Claude сначала понимает, что ему нужно местоположение пользователя, чтобы ответить на вопрос о погоде, поэтому он вызывает инструмент get_location.
  2. Пользователь (т.е. клиентский код) выполняет фактическую функцию get_location и возвращает результат “San Francisco, CA” в блоке tool_result.
  3. Теперь, когда местоположение известно, Claude переходит к вызову инструмента get_weather, передавая “San Francisco, CA” в качестве параметра location (а также предполагаемый параметр unit, поскольку unit не является обязательным параметром).
  4. Пользователь снова выполняет фактическую функцию get_weather с предоставленными аргументами и возвращает данные о погоде в другом блоке tool_result.
  5. Наконец, Claude включает данные о погоде в ответ на естественном языке на исходный вопрос.

Использование инструментов с цепочкой рассуждений

По умолчанию Claude 3 Opus получает указание подумать, прежде чем отвечать на запрос об использовании инструмента, чтобы лучше определить, необходим ли инструмент, какой инструмент использовать и какие параметры подходят. Claude 3 Sonnet и Claude 3 Haiku получают указание пытаться использовать инструменты как можно больше и с большей вероятностью вызовут ненужный инструмент или выведут отсутствующие параметры. Чтобы побудить Sonnet или Haiku лучше оценить пользовательский запрос перед вызовом инструментов, можно использовать следующую подсказку:

Подсказка с цепочкой рассуждений

Ответьте на запрос пользователя, используя соответствующие инструменты (если они доступны). Перед вызовом инструмента проведите некоторый анализ внутри тегов \<thinking>\</thinking>. Во-первых, подумайте, какой из предоставленных инструментов является подходящим для ответа на запрос пользователя. Во-вторых, просмотрите каждый из обязательных параметров соответствующего инструмента и определите, предоставил ли пользователь напрямую или дал достаточно информации, чтобы вывести значение. При решении, можно ли вывести параметр, тщательно рассмотрите весь контекст, чтобы увидеть, поддерживает ли он конкретное значение. Если все обязательные параметры присутствуют или могут быть разумно выведены, закройте тег thinking и продолжайте вызов инструмента. НО, если одно из значений для обязательного параметра отсутствует, НЕ вызывайте функцию (даже с заполнителями для отсутствующих параметров), а вместо этого попросите пользователя предоставить отсутствующие параметры. НЕ запрашивайте дополнительную информацию по необязательным параметрам, если она не предоставлена.


Режим JSON

Вы можете использовать инструменты, чтобы заставить Claude создавать вывод JSON, который следует схеме, даже если у вас нет намерения передавать этот вывод через инструмент или функцию.

При использовании инструментов таким образом:

  • Обычно вы хотите предоставить один инструмент
  • Вы должны установить tool_choice (см. Принудительное использование инструмента), чтобы указать модели явно использовать этот инструмент
  • Помните, что модель будет передавать input в инструмент, поэтому название инструмента и описание должны быть с точки зрения модели.

Следующий пример использует инструмент record_summary для описания изображения в определенном формате.

#!/bin/bash
IMAGE_URL="https://upload.wikimedia.org/wikipedia/commons/a/a7/Camponotus_flavomarginatus_ant.jpg"
IMAGE_MEDIA_TYPE="image/jpeg"
IMAGE_BASE64=$(curl "$IMAGE_URL" | base64)

curl https://api.anthropic.com/v1/messages \
     --header "content-type: application/json" \
     --header "x-api-key: $ANTHROPIC_API_KEY" \
     --header "anthropic-version: 2023-06-01" \
     --data \
'{
    "model": "claude-3-sonnet-20240229",
    "max_tokens": 1024,
    "tools": [{
        "name": "record_summary",
        "description": "Записать краткое описание изображения с использованием хорошо структурированного JSON.",
        "input_schema": {
            "type": "object",
            "properties": {
                "key_colors": {
                    "type": "array",
                    "items": {
                        "type": "object",
                        "properties": {
"r": { "type": "number", "description": "значение красного [0.0, 1.0]" },
"g": { "type": "number", "description": "значение зеленого [0.0, 1.0]" },
"b": { "type": "number", "description": "значение синего [0.0, 1.0]" },
"name": { "type": "string", "description": "Название цвета, понятное человеку, в формате snake_case, например \"olive_green\" или \"turquoise\"" }
                        },
                        "required": [ "r", "g", "b", "name" ]
                    },
                    "description": "Ключевые цвета на изображении. Ограничьте менее чем четырьмя."
                },
                "description": {
                    "type": "string",
                    "description": "Описание изображения. Максимум одно-два предложения."
                },
                "estimated_year": {
                    "type": "integer",
                    "description": "Предполагаемый год, когда было сделано изображение, если это фотография. Устанавливайте это только если изображение кажется нехудожественным. Приблизительные оценки допустимы!"
                }
            },
            "required": [ "key_colors", "description" ]
        }
    }],
    "tool_choice": {"type": "tool", "name": "record_summary"},
    "messages": [
        {"role": "user", "content": [
            {"type": "image", "source": {
                "type": "base64",
                "media_type": "'$IMAGE_MEDIA_TYPE'",
                "data": "'$IMAGE_BASE64'"
            }},
            {"type": "text", "text": "Опишите это изображение."}
        ]}
    ]
}'