Акты Становления

004: Агент/Вызов

Конкретный, исполняемый экземпляр инструмента, с определёнными значениями для его params. Это запрос, сфокусированный на вызове, который описывает, что должно быть сделано.

Протокол инструментов создаёт базовый интерфейс на основе схем, который позволяет агентам понимать структурированные возможности. Этот документ описывает протокол вызова, который основан на инструментах и определяет, как происходит исполнение.

Вызов — это конкретный экземпляр инструмента с определёнными значениями параметров, готовый к исполнению. Если инструменты определяют, что можно сделать, то вызовы определяют, как это будет исполнено.

На заметку

Запрос, который приводит к набору вызовов, является носителем. Носитель представляет собой единый реактивный момент принятия решения, когда агент выбирает из доступных инструментов, чтобы сформировать ответ.

Композиция и контекст

Сам по себе вызов — это простая структура данных. Его сила заключается в композиции с другими протоколами, которые управляют его средой исполнения. Эти протоколы активируются специальными мета-свойствами (с префиксом _) в схеме инструмента, что позволяет одному объекту вызова запускать различные сценарии исполнения.

Придавая этим мета-свойствам ясное семантическое значение, мы позволяем LLM активно участвовать в композиции. Модель может анализировать различные комбинации этих свойств для создания сложных и новых цепочек исполнения, переходя от простого выбора инструментов к динамической оркестрации рабочих процессов.

Tip

Следующий раздел объясняет связи с другими частями системы, которые будут подробно описаны позже. Не нужно забегать вперёд, мы рассмотрим всё в логической последовательности. Вы сможете вернуться к этому разделу позже.

  • Явное исполнение (_activity): Самое фундаментальное расширение — это связывание вызова с детерминированной функцией кода. Свойство _activity указывает на то, что вызов должен быть исполнен действием, а не скрытыми рассуждениями LLM.

  • Делегированное исполнение (_delegate): Вызов может быть делегирован внешнему делегату. Свойство _delegate обычно содержит ссылку на сохранённый запрос (часто в виде пути к JSON-файлу), что позволяет вызывать этот запрос как многоразовый инструмент. Это обеспечивает изолированную «чистую комнату» для исполнения, предотвращая утечку контекста и обеспечивая настоящую инкапсуляцию.

  • Перенос контекста (_scopes): Протокол областей видимости контролирует, какой контекст доступен вызову. Его основное применение — сфокусировать внимание LLM во время скрытого исполнения, указывая, какие части родительского контекста следует учитывать. Это предотвращает утечку контекста и ведёт к более надёжным результатам. При использовании с _delegate его роль становится ещё более мощной: он строго определяет весь контекст для изолированного исполнения делегата.

  • Исполнение с сохранением состояния (_outputPath): Вызов можно сделать сохраняющим состояние, указав ему, куда записывать результат. Свойство _outputPath определяет путь в постоянном состоянии, где должен храниться результат вызова. Это позволяет создавать многоэтапные рабочие процессы, в которых результат одного вызова может использоваться как входные данные для другого.

  • Исполнение экземпляров (_instance): Вызов может быть нацелен на конкретный экземпляр в рамках запроса с несколькими экземплярами. Свойство _instance действует как уникальный идентификатор, фокусируя все операции этого вызова (например, чтение входных данных из состояния и запись результатов в него) на определённом контексте. Это обеспечивает эффективную параллельную обработку нескольких состояний с одним и тем же набором инструментов.

Паттерны исполнения вызовов

Когда агент генерирует несколько вызовов, можно применять различные стратегии исполнения в зависимости от потребностей приложения:

// Исполнение одного вызова
const result = await Tool(call);

// Исполнить все вызовы, дождаться всех результатов
const results = await Tool.all(calls);

// Исполнить все вызовы, вернуть первый успешный результат
const result = await Tool.any(calls);

// Исполнить все вызовы, вернуть первый завершённый (успешно или с ошибкой)
const result = await Tool.race(calls);

Эти паттерны позволяют:

  • Тонкая настройка: Обрабатывать вызовы по отдельности с пользовательской логикой между исполнениями
  • Пакетная обработка: Исполнять независимые вызовы параллельно для максимальной производительности
  • Стратегии быстрого отказа: Останавливаться при первом успехе (.any()) или первом завершении (.race())
  • Операции «всё или ничего»: Гарантировать, что все вызовы выполнятся успешно вместе (.all()), поддерживая согласованность, когда вызовы логически сгруппированы

Оркестрация вызовов в цикле

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

Следующий документ, 005: Агент/Цикл, подробно описывает этот цикл исполнения.