# ГЛАВА 11. НЕ ЗАСТАВЛЯЙ МОДЕЛЬ СЧИТАТЬ — ДАЙ ЕЙ ИНСТРУМЕНТ Представьте блестящего лингвиста, который свободно говорит на 50 языках, мгновенно схватывает контекст и нюансы, улавливает иронию и подтекст. А теперь попросите его перемножить два четырёхзначных числа в уме. Он попытается — и, скорее всего, ошибётся. Не потому что глуп, а потому что его мозг заточен под другое. LLM — именно такой лингвист. Просить модель считать — это как просить переводчика доказывать теоремы: он понимает *слова* в формулах, но не выполняет *операции*. Решение очевидно: дай лингвисту калькулятор. Code Interpreter или любой другой **code execution sandbox** — это и есть калькулятор. А в более широком смысле, инструменты (tools) превращают LLM из одинокого эрудита в **менеджера, который знает ЧТО нужно сделать и делегирует КАК — специалистам**: Python считает, база данных ищет, API действует. Эта глава — о том, почему делегирование работает, и как выстроить архитектуру, в которой модель управляет, а не считает. --- ## 11.1. Почему LLM плохо считают: числовые отношения vs точная арифметика ### Корень проблемы: токенизация чисел Как мы выяснили в [Главе 1](01_tokens_vectors_and_semantic_space.md), числа токенизируются как текстовые фрагменты, а не как математические объекты: ``` "247 × 13" → ["247", " ×", " 13"] — три текстовых токена ``` Модель не имеет арифметического блока. Она не выполняет умножение. Она **предсказывает**, какие цифры скорее всего следуют за последовательностью `247 × 13 = `. Это принципиально разные операции. ### Что модель может | Задача | Надёжность | Механизм | |--------|------------|----------| | Сравнение порядков величин | Хорошо | Статистические ассоциации (`миллион > тысяча`) | | Простая арифметика (2 + 3) | Хорошо | Заучено из тренировочных данных | | Умножение 2–3-значных | Ненадёжно | Частично заучено, частично угадывает | | Умножение 4+ -значных | Плохо | Недостаточно примеров, вероятностная аппроксимация | | Проценты и дроби | Ненадёжно | Путает числитель/знаменатель | | Статистические расчёты | Плохо | Нет арифметического блока | | Float precision | Плохо | `0.1 + 0.2` может дать `0.3` или `0.30000000000000004` | ### Эксперимент: момент истины Попробуйте прямо сейчас. Откройте любой чат с LLM **без** Code Interpreter и спросите: ``` "Вычисли 7823 × 4291" ``` Верный ответ: **33 568 493**. Модель ответит что-то вроде: `33 571 993` — ошибка на три тысячи. Выглядит правдоподобно, начинается с тех же цифр, но это не результат вычисления — это **статистическая галлюцинация**. Модель предсказала, какие цифры вероятнее всего идут после `7823 × 4291 =`, точно так же, как она предсказывает следующее слово в предложении. Теперь задайте тот же вопрос модели, у которой включён инструмент выполнения кода: ```python print(7823 * 4291) # → 33568493 ✓ ``` Каждый раз — точный ответ. Не потому что модель стала умнее, а потому что она **делегировала**: написала однострочник на Python и отдала его интерпретатору. Лингвист взял калькулятор. Усложним: `"Посчитай (7823 × 4291) + (1597 × 863) − 42.7%"`. Без инструмента модель сфантазирует уверенный, но неверный ответ. С Python — выдаст точный результат с промежуточными шагами. Вот почему **Code Interpreter — не фича, а необходимость**. --- ## 11.2. PAL и Tool Use: делегируй вычисление ### PAL: Program-Aided Language Models (пошаговый разбор) PAL (Gao et al., 2023) — идея элегантна в своей простоте: вместо того чтобы решать задачу самостоятельно, LLM генерирует **программу**, которая решает задачу за неё. Модель остаётся в своей зоне силы — понимание языка и генерация кода, — а вычисления уходят туда, где им место: в интерпретатор. Разберём по шагам: **Шаг 1. Входная задача на естественном языке:** ``` "В магазине было 48 яблок. Продали 1/3. Потом привезли ещё 20. Сколько яблок?" ``` **Шаг 2. Модель транслирует текст в код** (это её сильная сторона — понимание текста): ```python apples = 48 sold = apples // 3 # "продали 1/3" → 16 remaining = apples - sold # "осталось" → 32 delivered = 20 # "привезли ещё 20" total = remaining + delivered print(total) # → 52 ``` **Шаг 3. Python выполняет код** и возвращает: `52` **Шаг 4. Модель формулирует ответ:** «В магазине 52 яблока.» Обратите внимание: на шагах 1, 2 и 4 работает LLM (язык → код → язык). На шаге 3 — Python (арифметика). Каждый делает то, в чём силён. **Почему PAL надёжнее, чем Chain-of-Thought арифметика:** - Каждый шаг фиксирован в коде — нет скрытых ошибок рассуждения. - Арифметика выполняется Python, а не нейронной сетью. - Промежуточные значения видимы для отладки. - Код можно проверить ревьюером — или другой LLM. ### Паттерн: Code Interpreter / code execution К 2026 году выполнение кода перестало быть экзотикой, но важно различать **три разные вещи**: 1. **Потребительский продукт** (например, ChatGPT с Advanced Data Analysis). 2. **API tool** (например, `code_interpreter` у OpenAI или `code_execution` у Anthropic/Gemini). 3. **Локальный оркестратор** (ваш sandbox, Docker, локальный Python, bash tool). Во всех трёх случаях идея одна и та же: модель пишет код, а исполняет его отдельная среда. Но включение, права доступа, файловая система и сеть различаются. Через API схема остаётся явной — вы определяете инструмент в JSON Schema, модель его вызывает. У OpenAI это `tools` с `type: "function"` в Responses API; у Anthropic — `tools` с `input_schema`; у Gemini — `function_declarations`. Все три провайдера используют JSON Schema для описания параметров — определения инструментов фактически переносимы между платформами, а MCP делает эту переносимость стандартом (подробнее — в §11.4). > **Промпт для генерации:** «Напиши определение tool use-инструмента `execute_python` для [Anthropic Messages API / OpenAI Responses API] — инструмент принимает строку с Python-кодом и возвращает stdout/stderr. Добавь `input_schema` / `parameters` с JSON Schema и обязательное поле `code`. Покажи, как передать этот инструмент в вызов API и как обработать `tool_use` / `tool_calls` в ответе.» Модель **сама** решает, когда вызвать code execution: - Простой факт → ответ из памяти. - Вычисление → генерирует Python, запускает, возвращает результат. - Визуализация → matplotlib, возвращает изображение. - Работа с файлами → читает CSV/JSON, обрабатывает, строит графики. **Function calling / tool use стал стандартным интерфейсом, но не единым рантаймом.** OpenAI, Anthropic и Google поддерживают структурированные tool-вызовы, а open-weight экосистема научилась их эмулировать через frameworks. Но схемы, approval-flow, JSON-валидация и способность надёжно выбирать нужный инструмент всё ещё отличаются по платформам и моделям. ### Четыре типа инструментов Инструменты делятся по характеру действия. Это важно для архитектуры — разные типы требуют разных уровней доверия: **1. Вычисление (computation)** — чистые функции без побочных эффектов: | Задача | Инструмент | Почему не LLM | |--------|-----------|---------------| | Арифметика | Python / Calculator | Нет arithmetic head | | Regex | `re` module | Сложные regex → ошибки при генерации | | Форматирование | `json.dumps`, `yaml.dump` | Гарантированная структура | | Статистика | numpy / pandas | Точность floating point | **2. Получение данных (data retrieval)** — только чтение, без изменений: | Задача | Инструмент | Почему не LLM | |--------|-----------|---------------| | Поиск фактов | RAG / Web Search | Параметрическая память устаревает | | SQL-запросы | База данных (SELECT) | Модель может ошибиться в JOIN | | Дата/время | `datetime` / API | Модель не знает «сегодняшнюю» дату | | Файлы (чтение) | File system API | Модель не видит файловую систему | **3. Действия (write/mutate)** — изменения во внешнем мире (требуют подтверждения!): | Задача | Инструмент | Риск | |--------|-----------|------| | Отправка email | SMTP API | Необратимо | | Запись в БД | INSERT/UPDATE | Изменяет данные | | Создание задачи | Jira / Linear API | Видно команде | | Деплой | CI/CD API | Влияет на production | **4. Коммуникация (communication)** — взаимодействие с пользователями и системами: | Задача | Инструмент | Особенность | |--------|-----------|------| | Уведомления | Slack / Teams API | Проверьте тон и содержание | | Ответ пользователю | Chat UI | Финальный этап цепочки | | Логирование | Observability API | Для отладки и аудита | **5. Управление компьютером (computer use)** — прямое взаимодействие с графическим интерфейсом: | Задача | Инструмент | Особенность | |--------|-----------|------| | Действия в браузере | Browser automation / Operator | Навигация, заполнение форм, скриншоты | | Взаимодействие с десктопом | Screenshot + mouse/keyboard | Управление приложениями без API | | Тестирование UI | Computer Use API | Воспроизведение пользовательских сценариев | Computer use — качественно новый тип инструмента, появившийся в production-доступе в 2025–2026. В отличие от четырёх предыдущих типов, модель взаимодействует не через API, а через **визуальный интерфейс**: делает скриншот экрана, анализирует его и отправляет команды мыши и клавиатуры. Anthropic предоставляет computer use в бета-режиме (`computer_20251124`), OpenAI — как встроенный инструмент для GPT-5.4 (75 % на бенчмарке OSWorld-Verified). **Требования к безопасности** у computer use выше, чем у любого другого типа инструментов. Модель видит содержимое экрана — а значит, уязвима к prompt injection через визуальный контент (текст на странице, изображения с инструкциями). Используйте изолированное окружение (Docker, VM) и ограничивайте доступ к чувствительным приложениям. **Правило большого пальца:** вычисление и чтение — автоматически, действия и коммуникацию — с подтверждением человека (human-in-the-loop). Computer use — всегда с подтверждением и в sandbox. --- ## 11.3. Популярные технологии надёжнее экзотических ### Принцип: ищите не "магическую библиотеку", а кросс-вендорное пересечение Точный состав тренировочных данных закрытых frontier-моделей мы не видим. Поэтому фразу «эта библиотека точно была в train set у всех вендоров» нельзя честно доказывать по публичным данным. Но есть более надёжный инженерный proxy: **официальные runtime-документы самих платформ**. Когда OpenAI, Anthropic и Gemini независимо сходятся на одном и том же short list для code execution, это сильный сигнал, что именно этот стек будет и доступен, и хорошо поддержан пост-обучением, и привычен модели в инструментальном режиме. Самое важное наблюдение 2025–2026 годов: у Python-sandbox стеков разных провайдеров действительно есть большое пересечение. Повторяются одни и те же категории: табличная обработка, численные вычисления, графики, файлы Office/PDF, базовая статистика и символьная математика. ### Сверхстабильный short list для Python sandbox | Категория | Первый выбор | Когда использовать | Почему это надёжно | |-----------|--------------|--------------------|--------------------| | **Табличные данные** | `pandas` | CSV, Excel, groupby, joins, cleanup | Официально подтверждён у OpenAI; также входит в sandbox Anthropic и Gemini | | **Графики** | `matplotlib` | Линейные, столбчатые, scatter, отчётные chart'ы | OpenAI прямо говорит про Matplotlib; Gemini поддерживает только `matplotlib` для graph rendering | | **Численные вычисления** | `numpy`, `scipy` | массивы, статистика, оптимизация, scientific helpers | Есть в Anthropic и Gemini; это де-факто базовый численный слой Python | | **Excel I/O** | `openpyxl` | читать/писать `.xlsx`, править workbook'и | Повторяется в Anthropic и Gemini | | **Базовая статистика и ML** | `scikit-learn`, `statsmodels` | регрессии, baseline-классификация, простые метрики | Явно перечислены в Anthropic; `scikit-learn` также есть у Gemini | | **Символьная математика** | `sympy` | формулы, уравнения, algebraic manipulation | Есть в Anthropic и Gemini | | **Документы и отчёты** | `python-docx`, `python-pptx`, `reportlab` | DOCX/PPTX/PDF-артефакты | Anthropic и Gemini публикуют похожий набор | | **Файлы и изображения** | `pillow`, `pypdf`/`PyPDF2` | изображения, PDF, file transformations | Стабильная часть sandbox-экосистемы Anthropic и Gemini | Это не строгая теорема про training mix, но очень полезная operational policy: если агент может решить задачу на этом short list, почти всегда стоит начать именно с него. ### JS и artifact-side: React как безопасный первый выбор На JavaScript-стороне картина менее симметрична, потому что многие платформы выполняют код именно в Python, а не в Node.js sandbox. Но для Claude есть очень явный сигнал: в официальной документации по Artifacts среди типовых результатов и AI-powered UI прямо фигурируют **interactive React components** и rich UIs with React. Поэтому для browser-side прототипов, мини-инструментов и UI-обвязки вокруг модели разумный default — **React-first**, а не экзотический frontend-стек. Практический перевод этого наблюдения простой: если ваша цель — быстро получить рабочий AI-артефакт или интерактивный инструмент, React почти всегда безопаснее, чем niche framework с маленьким следом в экосистеме. ### Вне песочницы действует тот же принцип Даже когда задача не сводится к sandbox-коду, общая закономерность сохраняется: mainstream-технологии модель генерирует и чинит надёжнее, чем редкие или слишком новые. | Технология | Представленность в открытой экосистеме | Качество генерации | |------------|----------------------------------------|-------------------| | Python + `requests` / `httpx` | Очень высокая | Отлично | | JavaScript + `fetch` | Очень высокая | Отлично | | SQL (PostgreSQL, MySQL) | Очень высокая | Хорошо | | Go + `net/http` | Высокая | Хорошо | | Rust + `tokio` | Высокая и растущая | Хорошо | | Terraform / Kubernetes YAML | Высокая | Хорошо | | React / Next.js | Очень высокая | Хорошо | | Elixir + Phoenix | Умеренная | Средне | | Zig / V / Nim | Низкая | Ненадёжно | | Кастомный DSL | Почти нулевая | Плохо без few-shot и валидации | ### Как определить preferred stack в новой среде 1. **Смотрите официальные docs runtime-а**, а не только бенчмарки модели. Если платформа перечисляет preinstalled libraries или официальные способы рендеринга, это сильнее догадок о train set. 2. **Ищите пересечение между провайдерами.** Чем больше overlap у OpenAI, Anthropic, Gemini и похожих сред, тем выше шанс, что решение будет переносимым. 3. **Отмечайте библиотеки из официальных примеров.** Если документация снова и снова показывает `pandas`, `matplotlib` и `React`, это хороший сигнал для default choice. 4. **Проверяйте sandbox-ограничения.** Например, Gemini разрешает много библиотек, но для графиков официально поддерживает именно `matplotlib`; значит, `matplotlib-first` — не эстетический выбор, а operational constraint. ### Как использовать short list эффективно 1. В system prompt или project rules явно пишите: **"сначала решай задачу на standard stack"**. 2. Для таблиц начинайте с `pandas`; переходите к `numpy`/`scipy`, только если нужен более низкий уровень математики. 3. Для графиков default = `matplotlib`, если вам важна переносимость между sandboxes. 4. Для Excel используйте `openpyxl`, а не малоизвестные обёртки. 5. Для символьных задач используйте `sympy`, а не самодельный парсер формул. 6. Для AI-артефактов и UI-прототипов в Claude задавайте React как предпочтительный frontend. 7. Разрешайте переход на niche library только после короткого объяснения, почему short list недостаточен. > **Практический policy-prompt:** «При работе в sandbox предпочитай следующий стек по умолчанию: `pandas`, `matplotlib`, `numpy`, `scipy`, `openpyxl`, `scikit-learn`, `sympy`, `pillow`, `python-docx`, `python-pptx`, `reportlab`. Сначала предлагай решение на этом стеке. Переход на нишевую библиотеку допускается только если ты кратко объяснил, почему standard stack не покрывает задачу. Для UI-артефактов предпочитай React.» ### Практические рекомендации 1. **Python + стандартная библиотека + short list** — первый выбор для вычислений и data tasks. 2. **`ast` + sandbox** — для безопасного выполнения сгенерированного кода. 3. **Стандартные API** (REST, GraphQL) — для интеграций. 4. **Проверенные библиотеки** (`pandas`, `numpy`, `openpyxl`, `matplotlib`) — раньше кастомных обёрток. 5. **Фреймворки оркестрации** (LangChain Tools, LlamaIndex Tools, Anthropic tool use, OpenAI Responses API) — стандартные паттерны вместо велосипедов. > **Промпт для генерации песочницы:** «Напиши Python-функцию `safe_execute(code: str) -> (stdout, stderr)` для безопасного выполнения LLM-сгенерированного кода. Требования: (1) AST-проверка — запретить import os/subprocess/shutil/sys и вызовы exec/eval/\_\_import\_\_; (2) ограниченный `__builtins__` — только print, range, len, числовые типы, коллекции, sorted, enumerate; (3) перехват stdout через StringIO; (4) timeout через signal или threading. Для production предпочтительнее Docker/VM-песочница или серверный инструмент (`code_execution` у Anthropic, `code_interpreter` у OpenAI).» --- ## 11.4. Экосистема MCP: как модели получили доступ ко всему ### Что такое MCP Model Context Protocol (MCP) — открытый стандарт, который позволяет LLM подключаться к внешним инструментам через единый интерфейс. Если function calling — это способность модели вызывать функции, то MCP — это стандартизация того, **как эти функции обнаруживаются, описываются и вызываются**. Думайте о нём как о USB для AI: один разъём, много устройств. MCP создан Anthropic в конце 2024 года, но к 2025 году перешёл под управление **Linux Foundation** (LF Projects, LLC) и управляется MCP Steering Group. Текущая версия спецификации — `2025-11-25`. Протокол построен на JSON-RPC 2.0 и поддерживает два транспорта: **STDIO** (локальный процесс, без сетевых задержек) и **Streamable HTTP** (удалённые серверы, поддержка OAuth-аутентификации). MCP-сервер предоставляет клиенту три типа примитивов: - **Tools** — вызываемые функции (discovery через `tools/list`, исполнение через `tools/call`). - **Resources** — источники данных для контекста (файлы, БД, API). - **Prompts** — переиспользуемые шаблоны взаимодействия. Базовая концепция MCP и её связь с агентным контуром рассмотрены в [Главе 10](10_agent_not_chat.md). Здесь мы сосредоточимся на экосистеме, нативной поддержке в API и принципах выбора серверов. ### Нативная поддержка MCP в API провайдеров Ключевое событие 2025–2026: оба крупнейших провайдера встроили MCP-клиент прямо в свои API. Это значит, что один MCP-сервер, написанный один раз, работает и с Claude, и с ChatGPT, и с VS Code, и с десятками других клиентов. | Провайдер | Механизм | Что поддерживается | |-----------|----------|-------------------| | **OpenAI** | `type: "mcp"` в Responses API | Удалённые MCP-серверы (Streamable HTTP, SSE). Connectors — готовые MCP-обёртки для Dropbox, Gmail, Google Drive, Outlook, Teams, SharePoint и др. | | **Anthropic** | MCP Connector в Messages API (бета-заголовок `mcp-client-2025-11-20`) | Удалённые MCP-серверы по URL. Пока только tool calls (не resources/prompts через API). | | **VS Code / Copilot** | Встроенная поддержка MCP-серверов | Локальные и удалённые серверы, конфигурация в settings | | **Cursor, Claude Code** | Конфигурация MCP-серверов | Поддержка STDIO и HTTP транспортов | Не все клиенты поддерживают все примитивы — в production проверяйте transport, approval-flow и security-модель конкретного клиента. ### Экосистема MCP-серверов в 2026 году К апрелю 2026 года экосистема MCP взрывно выросла: 80 000+ звёзд на GitHub, 100+ официальных интеграций, 10+ SDK на разных языках (официальные: TypeScript, Python; community: Java, Kotlin, Go, Rust, C#, Ruby, PHP, Swift). | Категория | Примеры MCP-серверов | Что даёт модели | |-----------|----------------------|------------------| | Базы данных | PostgreSQL, SQLite, MongoDB, Snowflake | Чтение/запись данных | | API и SaaS | GitHub, Slack, Jira, Linear, Stripe | Управление проектами и сервисами | | Файловые системы | Локальные файлы, Google Drive, S3 | Чтение/запись файлов | | Инфраструктура | Kubernetes, Docker, AWS, Cloudflare | Управление инфраструктурой | | Поиск | Brave Search, Google, Exa | Веб-поиск в реальном времени | | Разработка | Git, терминал, LSP, Firebase | Работа с кодом и репозиториями | | Мониторинг | Sentry, Datadog, Grafana | Анализ логов и метрик | Для создания собственных MCP-серверов существуют фреймворки: FastMCP, Spring AI MCP, Quarkus MCP, Vercel MCP Adapter — и даже автогенераторы из OpenAPI-спецификаций (FastAPI-to-MCP). ### Как найти нужный MCP-сервер - **MCP реестр** (modelcontextprotocol.io) — каталог проверенных серверов, управляемый MCP Steering Group. - **GitHub** — поиск по `topic:mcp-server`. - **npm / PyPI** — пакеты с префиксом `mcp-server-*`. - **OpenAI Connectors** — готовые интеграции для популярных SaaS (не требуют отдельного MCP-сервера). ### A2A: протокол для взаимодействия агентов MCP решает задачу «агент ↔ инструмент». Но что если нужно, чтобы **агент взаимодействовал с другим агентом** — например, агент-планировщик делегирует подзадачу агенту-исполнителю на другом сервере? Для этого Google предложил **A2A (Agent-to-Agent Protocol)** — протокол обнаружения и коммуникации между автономными агентами. A2A и MCP не конкурируют, а дополняют друг друга: MCP стандартизирует доступ к инструментам и данным, A2A — оркестрацию между агентами. Существует «A2A MCP Server» — мост, позволяющий MCP-клиенту вызывать A2A-агентов как обычные инструменты. В production-системах с несколькими специализированными агентами стоит рассматривать связку MCP + A2A. Для систем с одним агентом и набором инструментов — достаточно MCP. ### Пример: как модель использует MCP ``` Пользователь: "Какие баги были заведены на этой неделе?" Модель (думает): Нужна информация из Jira → вызову MCP-сервер Jira Модель → MCP Jira: tools/call search_issues(type="Bug", created_after="2026-04-03") MCP Jira → Модель: [список из 12 багов с ключами, статусами, assignee] Модель → Пользователь: "На этой неделе заведено 12 багов, из них 3 критичных..." ``` Модель выступила менеджером: поняла запрос, выбрала нужный инструмент, сформулировала параметры и пересказала результат человеческим языком. --- ## 11.5. Принципы проектирования инструментов Недостаточно дать модели инструменты — нужно, чтобы она **понимала**, когда и как их использовать. Это целиком зависит от того, как вы опишете инструмент. ### 1. Имя: глагол + существительное ``` ✓ search_issues, create_user, get_file_contents, run_sql_query ✗ do_thing, helper, process, handle ← модель не поймёт, когда вызывать ``` ### 2. Описание: когда использовать, а не только что делает ``` ✗ Плохое описание: "description": "Search for issues" ← какие issues? когда? ✓ Хорошее описание: "description": "Search Jira issues by type, status, assignee, or date range. Use when the user asks about bugs, tasks, or project progress. Returns issue key, title, status, and assignee." ``` ### 3. Параметры: строгая типизация + enum где возможно ``` ✗ Модель будет гадать формат: "date": {"type": "string"} ✓ Формат явный: "date": {"type": "string", "format": "date", "description": "ISO 8601: YYYY-MM-DD"} "status": {"type": "string", "enum": ["open", "in_progress", "closed"]} ``` ### 4. Меньше инструментов — лучше Каждый инструмент в списке — это токены в контексте. 5–15 инструментов — оптимально. 50+ — модель начнёт путаться и выбирать не тот. Лучше один инструмент `search_database(query, table)`, чем десять `search_users`, `search_orders`, `search_products`... **Tool search: масштабирование за 15 инструментов.** Правило «5–15 инструментов» работает при передаче всех определений в контекст. Но в MCP-экосистемах с десятками серверов и сотнями инструментов это ограничение становится проблемой. GPT-5.4 (OpenAI, март 2026) ввёл **tool search** — механизм, при котором модель получает лёгкий индекс инструментов (имя + краткое описание), а полные определения подгружает по запросу. По данным OpenAI, tool search снизил потребление токенов примерно вдвое при сохранении accuracy на внутреннем бенчмарке с десятками MCP-серверов (детали методологии не опубликованы). Если вы строите систему с большим числом MCP-серверов — проверьте, поддерживает ли ваш клиент lazy tool loading. Это реальный рычаг снижения стоимости inference в агентных контурах. ### 5. Возвращайте структурированные данные, не прозу Модель лучше работает с JSON, чем с произвольным текстом. Возвращайте `{"count": 12, "critical": 3, "items": [...]}`, а не `"Found 12 bugs, 3 critical"`. --- ## 11.6. Шкала важности 1–10: используйте для ранжирования, не для метрик ### Проблема с абсолютными числами Когда вы просите модель: «Оцени важность по шкале от 1 до 10», она возвращает число. Но это число **не калибровано**: модель не имеет внутренней шкалы, привязанной к реальности. ``` Промпт: "Оцени серьёзность бага по шкале 1-10" Баг: "Опечатка в логе" → Модель: "3" Баг: "SQL injection" → Модель: "9" Баг: "Race condition в платёжном модуле" → Модель: "8" ``` Проблема: **8 vs 9** — значимая разница? Или модель просто случайно выбрала числа? При повторном запуске может быть 7 и 8 или 9 и 9. ### Когда числовые оценки полезны **Для ранжирования** (relative ordering): модель стабильно ставит SQL injection выше опечатки. Порядок надёжнее абсолютных значений. **Для категоризации** (binning): `1–3 = low`, `4–7 = medium`, `8–10 = high`. Широкие бины устойчивы к шуму. ### Когда использовать инструменты вместо оценок | Задача | LLM-оценка | Инструмент | |--------|------------|-----------| | «Насколько сложен код?» | Субъективно | Cyclomatic complexity (radon) | | «Насколько длинный текст?» | Угадывает | `len(text.split())` | | «Какой прирост производительности?» | Не может | Benchmark (timeit) | | «Уязвим ли код?» | Может пропустить | SAST tools (semgrep, bandit) | | «Соответствует ли API стандарту?» | Неточно | Schema validator | --- ## 11.7. Архитектура: LLM как менеджер, не исполнитель ### Правильная ментальная модель LLM — это менеджер, который прекрасно понимает, ЧТО нужно сделать, но не должен делать всё сам. Как хороший руководитель, он делегирует КАК специалистам: ``` LLM = Менеджер (понимание задачи, планирование, коммуникация) Python = Бухгалтер (вычисления) БД = Архивариус (поиск данных) API = Курьер (действия во внешнем мире) ``` LLM решает **что** делать и **почему**. Tools выполняют **как**: ``` ┌─────────────────────────────┐ │ LLM │ │ "Нужно посчитать налог" │ │ → Сгенерировать Python │ │ → Результат: $12,450 │ │ → Сформировать ответ │ └───────────┬─────────────────┘ │ tool call ▼ ┌─────────────────────────────┐ │ Python Executor │ │ income = 85000 │ │ tax = income * 0.22 │ │ deductions = 6300 │ │ total = tax - deductions │ │ → return 12450.0 │ └─────────────────────────────┘ ``` ### Anti-pattern: заставлять LLM быть калькулятором ``` ✗ "Посчитай стоимость 247 единиц товара по $13.99 каждая, с НДС 20%, скидкой 5% для объёма > 200 единиц" ✓ "Сгенерируй Python-код для расчёта стоимости: - Количество: 247 - Цена за единицу: $13.99 - НДС: 20% - Скидка: 5% (при объёме > 200) Выведи промежуточные значения и финальную сумму." ``` --- ## 11.8. Computer use и browser automation ### Сдвиг парадигмы: от API к UI-действиям Не все системы имеют API. Legacy-приложения, внутренние порталы, сторонние SaaS без публичного интерфейса — единственный способ автоматизации для них — это взаимодействие с графическим интерфейсом. Computer use (Anthropic) и browser automation (OpenAI Operator, Playwright-based агенты) превращают GUI в ещё один tool surface. Важно: это **не** screen scraping и не macro-recording. Модель анализирует скриншот, распознаёт элементы интерфейса, принимает решение о следующем действии на основе текущего визуального состояния. Каждый шаг — полноценный inference-вызов с reasoning, а не воспроизведение записанного сценария. В §11.2 мы выделили computer use как пятый тип инструментов. Здесь — инженерная механика: как это работает, где ломается и когда стоит применять. ### Механика: screenshot → perception → action Цикл computer use повторяет стандартный agent loop ([Глава 10](10_agent_not_chat.md)), но вместо JSON-ответа от API модель получает **изображение** экрана: 1. **Screenshot** — агент делает снимок экрана (или окна браузера) и передаёт его модели как изображение. 2. **Perception** — vision-capable модель анализирует скриншот: распознаёт кнопки, поля ввода, текст, меню. 3. **Action** — модель возвращает действие: `click(x, y)`, `type("text")`, `scroll(direction)`, `key("Enter")`. 4. **Re-screenshot** — после выполнения действия делается новый скриншот, и цикл повторяется. Две ключевые проблемы механики: - **Coordinate scaling.** Координаты клика зависят от разрешения скриншота. Если скриншот сделан в одном разрешении, а действие выполняется в другом — промах мимо элемента. Решение: фиксированное разрешение скриншотов и нормализация координат. - **Нестабильность UI.** Интерфейс — живая система: появляются popup-окна, элементы перемещаются после загрузки, страница перерисовывается. Нужна retry-логика с повторным скриншотом и переоценкой ситуации. ### Инженерные проблемы | Проблема | Суть | Решение | |----------|------|--------| | Sandboxing | Агент имеет доступ ко всему экрану — файлы, пароли, другие приложения | Запуск в изолированной VM или контейнере с минимальным набором приложений | | Prompt injection через UI | Вредоносный контент на странице может перенаправить агента (текст, изображение с инструкцией) | Фильтрация OCR-контента, ограничение доменов, мониторинг отклонений от плана | | Coordinate scaling | Разрешение скриншота ≠ разрешение экрана → промахи | Фиксированное разрешение, калибровка координат | | Approval gates | Необратимые действия: удаление данных, оплата, отправка сообщений | Human-in-the-loop checkpoint перед каждым destructive action | | End-to-end верификация | Как убедиться, что действие выполнено корректно | Post-action screenshot → LLM-верификация результата | | Observability | Отладка GUI-автоматизации значительно сложнее отладки API-вызовов | Запись видео сессии, логирование каждого шага с скриншотом и action | ### Когда использовать, а когда нет **Используй computer use, когда:** - Нет API (legacy-система, внутренний портал, сторонний SaaS). - Нужна визуальная верификация (проверить, что UI отображает правильные данные). - End-to-end тестирование пользовательских сценариев. - Прототипирование автоматизации до появления API-интеграции. **НЕ используй, когда:** - Есть API — он всегда предпочтительнее по скорости, надёжности и стоимости. - Нужна высокая скорость — каждый шаг computer use требует inference-вызов + screenshot. - Нужна надёжность >99% — GUI нестабилен, элементы смещаются, появляются рекламные баннеры. - Обрабатываются чувствительные данные без возможности изолировать окружение. ### Безопасность Computer use — самый рискованный тип инструмента из пяти, описанных в §11.2. Модель видит содержимое экрана целиком и может выполнять произвольные действия с клавиатурой и мышью. Ключевое правило: **computer use agent работает в sandbox с минимальными привилегиями**. Не давайте доступ к production-системам без approval gate. Подробный разбор атак на computer use — включая визуальный prompt injection, click-jacking через UI-элементы и эксфильтрацию данных через скриншоты — в [Главе 15](15_llm_system_security.md), секции 15.5–15.6. --- ## Практический вывод ### Чек-лист делегирования | # | Правило | Действие | |---|---------|----------| | 1 | **Никогда не доверяйте арифметике модели** | Используйте code execution / calculator tool | | 2 | **Используйте function calling** | Определите tools для вычислений, поиска, API | | 3 | **Валидируйте типы и диапазоны** | Результат tool → проверка перед возвратом пользователю | | 4 | **Логируйте вызовы инструментов** | Для отладки и аудита | | 5 | **Предпочитайте mainstream** | Python > кастомный DSL | | 6 | **Sandbox** | Изолированное выполнение сгенерированного кода | | 7 | **Числовые оценки → для ранжирования** | Не для абсолютных метрик | | 8 | **Проектируйте инструменты для модели** | Чёткие имена, описания, типы, enum | | 9 | **Используйте MCP** | Стандартный протокол вместо кастомных интеграций | | 10 | **Computer use — в sandbox** | Изолированное окружение + human-in-the-loop | | 11 | **Computer use — не замена API** | Если есть API, используйте API | ### Задания **Задание 1. Проектирование набора инструментов.** Выберите реальный рабочий сценарий (например, «агент-помощник для DevOps» или «аналитик данных»). Составьте список из 5–10 инструментов, классифицируйте каждый по пяти типам из §11.2 и напишите для каждого: имя (глагол + существительное), description с указанием «когда использовать», JSON Schema параметров с типами и enum. Ожидаемый результат: готовый к использованию набор tool-определений, который можно подключить к любому провайдеру. **Задание 2. MCP — от нуля до рабочего сервера.** С помощью FastMCP или официального SDK (см. modelcontextprotocol.io) создайте MCP-сервер для внутреннего сервиса вашей команды (например, внутренняя вики или трекер задач). Реализуйте 2–3 инструмента и подключите сервер к Claude Desktop или VS Code. Ожидаемый результат: работающий MCP-сервер, который модель обнаруживает и вызывает в ответ на пользовательские запросы. **Задание 3. Делегирование vs самостоятельный ответ.** Составьте набор из 10 запросов, которые примерно поровну делятся на «модель справится сама» и «нужен инструмент». Отправьте их модели без инструментов и с инструментами, сравните результаты. Ожидаемый результат: понимание границы, где делегирование даёт выигрыш, а где добавляет лишнюю латентность. --- ## Источники - Gao, L., et al. (2023). "PAL: Program-aided Language Models." ICML. - Schick, T., et al. (2023). "Toolformer: Language Models Can Teach Themselves to Use Tools." NeurIPS 2023. arXiv:2302.04761. - Model Context Protocol Specification. (2025). LF Projects, LLC. https://spec.modelcontextprotocol.io/specification/ — spec version `2025-11-25`. - MCP Servers Repository. https://github.com/modelcontextprotocol/servers - OpenAI. “Tools, Connectors, and MCP.” Responses API Documentation. https://developers.openai.com/api/docs/guides/tools-connectors-mcp - Anthropic. “MCP Connector.” Claude Documentation. https://platform.claude.com/docs/en/agents-and-tools/mcp-connector - Anthropic. “Tool Use.” Claude Documentation. https://platform.claude.com/docs/en/agents-and-tools/tool-use - Anthropic. “Computer Use.” Claude Documentation. https://platform.claude.com/docs/en/agents-and-tools/computer-use - OpenAI. (2026). *Introducing GPT-5.4* — tool search, computer use. https://openai.com/index/introducing-gpt-5-4/ - Google. (2025). “Agent-to-Agent Protocol (A2A).” https://github.com/google/A2A - Qin, Y., et al. (2024). “Tool Learning with Foundation Models.” Nature Machine Intelligence. - OpenAI. “Data analysis with ChatGPT.” Help Center (updated 2026). pandas + Matplotlib, secure code execution environment with hundreds of Python libraries. https://help.openai.com/en/articles/8437071-data-analysis-with-chatgpt - Anthropic. “Code execution tool.” Claude API docs (2026). Pre-installed libraries for data science, visualization, file processing and math. https://platform.claude.com/docs/en/agents-and-tools/tool-use/code-execution-tool - Google. “Code execution.” Gemini API docs (updated 2026-03-25). Supported libraries and `matplotlib`-only graph rendering. https://ai.google.dev/gemini-api/docs/code-execution - Anthropic Help Center. “What are artifacts and how do I use them?” Interactive React components and AI-powered artifacts with React. https://support.anthropic.com/en/articles/9487310-what-are-artifacts-and-how-do-i-use-them --- **Навигация:** - Назад: [Глава 10. Агент ≠ Чат: разные режимы, разные правила](10_agent_not_chat.md) - Далее: [Глава 12. RAG: когда модели не хватает собственных знаний](12_rag.md)