The Jerusalem Post‘Armed to the teeth’: Syria buildup, Ankara involvement necessitated Israeli strikes - experts sayPunchPolice kill two suspected kidnappers, recover arms in AnambraESPN DeportesAmérica está muy cerca de fichar al delantero Miguel BorjaRTP DesportoPortugal no Azerbaijão para fazer história no Europeu feminino de voleibolESPNMultiple brawls mar Saints-Cowboys joint practiceוואלהדיווחים ערביים: תשעה הרוגים מתקיפות צה"ל בעיר עזהDaily MaverickGROUNDUP: Tulbagh factory closure threatens thousands of jobs, way of life20 MinutenAuch Schweizer Zahlungen: IS-Spenden als humanitäre Hilfe getarntDeadlineTrump, Trump, Trump: Kennedy Center Board Voted To Return POTUS’s Name To Three Different Spots On Complex’s GroundsNumeramaClaude peut désormais envoyer des mails à votre place, même sans validationRolling StoneNothing About Natalie Harp and Trump Is NormalNTVFurkan Vakfı soruşturmasında beş şirkete kayyum atandı
The Daily Newsstand · Free, Always
Wednesday, August 19, 2026

Чем Go полезен при разработке AI‑агентов

Translate

Всем привет! Меня зовут Илья Данилкин, я тимлид в  Авито Авто.

AI-агенты обычно живут рядом с Python, но всё же немало команд выбирают язык Go. Дело в том, что агенты большую часть времени не заняты сложными математическими расчётами, а ждут ответа модели или результата инструмента. А ещё работают в режиме бесконечных параллельных запусков. И если пользователь останавливает задачу, его запрос и следующие вызовы инструментов тоже нужно остановить.

Поэтому при выборе языка важны не только библиотеки для работы с моделями, но и то, как язык справляется с одновременными задачами, отменяет операции и насколько просто доставить готовое приложение пользователю. В Go для этого есть дешёвые горутины, context.Context и сборка в один бинарник.

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

Содержание

Почему агентная нагрузка подходит Go

В продакшене AI-агент живёт куда дольше обычного запроса к серверу. Запуски длятся долго: от нескольких секунд до нескольких часов, а не миллисекунды, как у веб-запроса. За это время агент успевает поработать в среде разработки, поуправлять сессией в браузере, разобрать документы — сделать то, чем без него занимался бы человек.

При этом агент почти не занят вычислениями: большую часть времени он проводит в ожидании ответа от модели, инструмента или человека. Агентная нагрузка — это параллельный сетевой сервис, только отдельные единицы работы в нём живут дольше. Go изначально проектировали именно для таких систем.

Для каждого запуска можно создать отдельную горутину. Каждая из них начинается примерно с 2 КБ стека, и планировщик распределяет их по всем ядрам процессора. Запуски преимущественно ожидают операции ввода-вывода, поэтому одна горутина на запуск обходится недорого, и собственная среда выполнения не становится узким местом. Пределом обычно становятся rate limits внешних LLM-провайдеров и объем памяти, который занимает каждый запуск, а не количество горутин. Всплеск CPU-нагрузки — например, десериализация большого результата работы инструмента — не приводит к остановке всего процесса, как это происходит в однопоточных средах выполнения, таких как Node или Python.

Источник

Источник

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

Ещё одна важная возможность — единая отмена операций через context.Context по всему дереву вызовов. Когда пользователь останавливает задачу, которая уже обошлась, условно, в десять долларов, он отменяет один контекст — и текущий запрос, и все последующие вызовы инструментов останавливаются. За уже сгенерированные токены он всё равно платит, но дорогая работа на следующих этапах прекращается. В Go соглашение об отмене более единообразное, чем в Python или Node. Если библиотека его игнорирует, это можно выявить с помощью goleak.

Подробнее об этом — в статье Дэниела Чалефа Building Agents in Go Without a Framework.

Тут еще больше контента

Тут еще больше контента

Почему базового агента можно написать без фреймворка

У Go уже есть агентные фреймворки — это ADK Go, Genkit Go, Eino, LangChainGo. Многие команды, которые работают на Go, не используют их, и на это есть две причины:

  • Разработчики на Go, как правило, избегают фреймворков и предпочитают стандартную библиотеку плюс небольшие зависимости. 

  • Опыт Anthropic показывает, что самые эффективные агенты используют простые компонуемые шаблоны, без фреймворков. 

Цикл, который управляет моделью, называется agent harness, или обвязка. Это код, который вызывает модель, запускает инструменты, которые она запрашивает, форматирует результаты, отслеживает состояние диалога и принимает решение о завершении. Модель выбирает следующий шаг, а harness выполняет его. Фреймворк предоставляет harness с настройками по умолчанию. Если писать вручную, получится около сорока строк.

История сообщений → вызов модели → есть tool calls? → параллельный запуск инструментов → добавление результатов в историю → новый вызов модели. Если tool calls нет, запуск завершается.

Работать без фреймворка — не значит писать HTTP-клиент вручную. Официальные SDK берут на себя работу с API провайдеров. anthropic-sdk-go и openai-go предоставляют типизированные сообщения, потоковую передачу и определения инструментов. Но сам harness они не запускают и запрошенные моделью инструменты за разработчика не выполняют. (На момент выхода статьи Чалефа это было так, но затем в anthropic-sdk-go добавили BetaToolRunner, который сам выполняет вызовы инструментов и ведёт цикл до итогового ответа. Для openai-go цикл по-прежнему собирают вручную.) 

Вы вызываете модель, проверяете ответ на tool-use blocks, запускаете инструменты, добавляете результаты в историю сообщений и вызываете модель снова. Поток управления, повторные попытки и точки сохранения состояния между этапами — это решения, которые вы принимаете самостоятельно.

При этом harness не хранит состояние между вызовами: история диалога хранится в слайсе сообщений, который передаётся функции и возвращается из неё, поэтому выполнение можно сохранить и продолжить на другом воркере. Вызовы инструментов одного хода выполняются параллельно, отмена контекста распространяется на все инструменты, а их ошибки возвращаются модели как результаты.

Функция-обвязка возвращает готовое сообщение; для потоковой передачи токенов к тому же интерфейсу добавляют callback или канал. Именно этот harness и оборачивает фреймворк.

Подробнее об этом — в статье Дэниела Чалефа Building Agents in Go Without a Framework.

Почему Go удобен для локальных агентных инструментов

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

Это видно на примере CRIT — локального инструмента для ревью планов и кода, созданных AI-агентами. Его автор Томаш Томчик обычно пишет на Elixir и предпочёл бы знакомый язык, но для CRIT выбрал Go. Дальше — его аргументы.

→ Go лучше подходит для сборки приложения в один бинарник. «Сборка Elixir-приложения в один бинарник официально не поддерживается. Есть пакет сообщества Burrito, который это позволяет, но такой сценарий не считается полноценной частью экосистемы, а бинарник получился бы намного больше. В Go сборка в один бинарник поддерживается как основной сценарий».

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

→ Стандартная библиотека Go закрывает почти все потребности продукта. «Стандартная библиотека Go закрыла примерно 95% того, что мне было нужно. Если переписывать продукт на Elixir, пришлось бы подключить намного больше сторонних пакетов. Это не обязательно плохо, но тогда мы начали бы отходить от идеи простого, компактного и лёгкого инструмента».

→ У Go есть готовый встроенный тулчейн. «У Go есть линтинг, встроенный форматтер и остальной тулчейн. Многое из этого есть и в Elixir, но в итоге Go лучше подошёл для лёгкого приложения в одном бинарнике».

→ Автоматические ограничения позволяют не проверять вручную весь код, созданный агентом. «Если я создаю продукт с помощью агентов, то всё равно не буду проверять каждую строку кода, даже если он написан на Elixir. Если Claude удобнее использовать Go для этой задачи, меня это устраивает. Я добавил в проект достаточно ограничений, чтобы не допускать мусорный код и другие проблемы».

Полный разговор — в подкасте Cup o' Go

Жми сюда!

Жми сюда!

Почему агенту недостаточно просто читать файлы

У Go уже есть развитый инструмент семантической работы с кодом, и теперь его возможностями могут пользоваться агенты. В gopls есть экспериментальный встроенный сервер Model Context Protocol. Он позволяет предоставлять AI-ассистентам часть возможностей gopls в виде MCP-инструментов.

MCP-сервер gopls — это обёртка над возможностями, которые gopls обычно предоставляет через Language Server Protocol. В документации gopls среди функций навигации перечислены:

  • Definition — переход к определению выбранного символа;

  • References — список ссылок на выбранный символ;

  • Implementation — отображение связей между интерфейсами и их реализациями;

  • Call Hierarchy — просмотр входящих и исходящих вызовов функции.

AI-агенты получают точные go-to-definition и references вместо grep по исходникам. MCP-сервер запускается командой gopls mcp.

Это новая экспериментальная функция для тех, кому интересны AI и LLM. Она может ещё измениться, но её уже можно попробовать.

Подробнее о возможностях и запуске MCP-сервера — в документации gopls. А в полном выпуске Cup o’ Go #162 — ещё и о Go 1.27 RC1, Delve 1.27, изменениях в gofmt и применении Go в игровой индустрии. 

Как на Go собрать локальное LLM-приложение

Агентное приложение на Go необязательно привязывать к удалённому LLM-провайдеру. Через Yzma оно напрямую работает с llama.cpp и запускает модель локально. К примеру, так устроено приложение с прогнозом погоды: вместо удалённого LLM-сервиса в нём используется открытая модель Gemma 4 (вариант E4B, ~4 млрд параметров). Yzma загружает её и запускает инференс в памяти как часть самого приложения, а Go-код формирует промпт, обрабатывает вызов инструмента, передаёт модели результат и продолжает генерацию. В итоге приложение полностью работает на устройстве.

Yzma — Go-пакет от Hybridgroup, команды, которая стоит за TinyGo и другими проектами. Yzma оборачивает llama.cpp (написанный на C++ рантайм для инференса LLM) и предоставляет ориентированные на Go абстракции для загрузки локальных моделей и выполнения инференса. Yzma упрощает подготовку библиотек llama.cpp и даёт инструменты, чтобы скачивать файлы моделей и управлять ими.

Когда модель загружена и настроена, взаимодействием с ней управляет функция runConversation. Приложение рассчитано на один запрос и выводит погоду, поэтому весь диалог сводится к пяти шагам.

Сначала код готовит промпты: сообщает модели задачу и объявляет доступный инструмент. Затем передаёт промпт модели и получает ответ. Дальше хост-приложение вызывает запрошенный инструмент и дополняет диалог его результатом — готовит результат в виде строки и передаёт в renderGemmaPromptWithToolResult. Получив промпт с ответом инструмента, модель генерирует итоговую сводку погоды по системным правилам форматирования.

Вся цепочка укладывается в один ход модели — в этом суть нативного вызова инструментов в Gemma 4. Так Go-приложение запускает Gemma 4 прямо на локальной машине: API-ключ не нужен, данные никуда не уходят.

Подробнее о том, как загрузить Gemma 4, подключить модель к Go-приложению и реализовать вызов инструментов, — в материале Building Gemma 4 Local-Powered LLM Apps with Go and Yzma. Примеры и документацию вы найдёте в репозитории Yzma.

Что ещё почитать и послушать о Go для AI-разработки

1. What’s New in Go: Google I/O 2026 Edition

Обзор новинок Go 1.25 и 1.26 — сборщик мусора Green Tea, векторные инструкции и модернизаторы кода в команде go fix. Эти новшества пригодятся и для AI-агентов, и для обычных микросервисов.

2. Accepted proposal: a goroutine leak profile in the Go standard library

Разбор нового профиля для поиска утечек горутин и сравнение с uber-go/goleak. Пригодится в долгоживущих агентных процессах, в которых отменённая задача не должна оставлять за собой незавершённые операции. И отдельная заметка о том, как итерация по каналу приводит к утечке горутин.

3. Claude as Your Performance Analysis Partner

Инженеры Red Hat показывают, как использовать Claude для анализа производительности Go-кода на примере сборщика Green Tea GC. Пример того, как AI помогает в работе над самими Go-системами. 

View the original on Хабр

KioskNews shows a cleaned-up reading view extracted from the publisher’s page — the original always lives on their site, not ours.