Сегодня разработка программного обеспечения с помощью AI часто идёт по простому процессу:
Написать описание задачи (prompt).
Позволить AI подготовить анализ и предложить решение.
Подготовить skills, агентов и субагентов.
Запустить реализацию.
Позволить AI написать код, протестировать его и исправить обнаруженные проблемы.
На первый взгляд это выглядит как идеальный процесс разработки. AI работает автономно, распределяет задачи между агентами, пишет тесты и постепенно завершает запрошенную функциональность.
И для небольших проектов такой подход может работать очень хорошо.
Если вы делаете простой интернет-магазин, корпоративный сайт на пять страниц или базовую административную систему, AI часто может выполнить значительную часть работы с очень хорошим результатом.
Почему?
Потому что миллионы разработчиков уже создавали похожее программное обеспечение.
Представьте два интернет-магазина. Один продаёт игрушки, другой - яблоки.
С точки зрения клиента это два разных бизнеса. С точки зрения архитектуры программного обеспечения они работают очень похоже:
Товары, организованные по категориям.
Управление ценами и складскими запасами.
Корзины покупок.
Обработка заказов.
Способы оплаты.
Управление клиентами.
Меняются в основном данные, специфические бизнес-правила и некоторые функции. Базовые архитектурные принципы остаются в целом теми же.
AI распознаёт эти паттерны, потому что встречал похожие структуры при обучении.
Проблема начинается тогда, когда вы перестаёте создавать обычное приложение и начинаете разрабатывать крупное корпоративное программное обеспечение.
Что происходит, когда система содержит от 300 000 до 500 000 строк кода?
Представьте корпоративное приложение с сотнями тысяч строк кода, десятками модулей, сотнями зависимостей и сложными бизнес-правилами.
Такая система могла развиваться несколько лет. За это время накопились архитектурные решения, исключения, исторические зависимости и бизнес-правила.
Не все из них задокументированы.
Один метод может влиять на десять других модулей. Изменение одного параметра может нарушить выставление счетов, права пользователей или обработку заказов.
Теперь представьте, что в эту среду вводится AI-агент.
Вы даёте ему задачу:
«Измени процесс оплаты так, чтобы он поддерживал дополнительный способ оплаты. Сохрани обратную совместимость и протестируй всё».
Агент составляет план, распределяет работу между субагентами, реализует изменения, запускает тесты и возвращает результаты.
Всё может выглядеть правильно.
Но прохождение тестов не обязательно означает, что программа сохранила все существующие бизнес-правила.
И это подводит нас к проблеме, которая полностью изменила мой подход к AI-агентам шесть месяцев назад.
Эксперимент, изменивший мой взгляд на агентные системы
Шесть месяцев назад я провёл эксперимент, который заставил меня пойти другим путём, вместо того чтобы просто создавать всё больше агентов и субагентов.
До тех пор я исходил из предположения, которое разделяют многие разработчики:
Чем лучше я распределяю задачи между специализированными агентами и чем больше механизмов проверки вводю, тем надёжнее будет результат.
Но в ходе экспериментов я столкнулся с фундаментальным вопросом:
Как агент может правильно реализовать бизнес-правило, если он даже не знает, что это правило существует?
И как другой агент может надёжно проверить результат, если у него тоже нет полной информации о том, как система должна себя вести?
Я начал изучать, как контекст передаётся между агентами.
Я обнаружил, что то, как информация передаётся и интерпретируется, может стать одним из самых слабых мест всего процесса.
Как на самом деле работают агенты и субагенты?
На практике существуют два распространённых подхода к коммуникации между AI-агентами.
1. Иерархическая модель – главный агент координирует субагентов
Эту архитектуру обычно называют Hub-and-Spoke или Star Topology (звёздная топология).
Принцип прост:
Пользователь передаёт задачу главному агенту.
Главный агент анализирует задачу и разбивает её на более мелкие части.
Он создаёт или активирует субагента A и даёт ему инструкции.
Субагент A выполняет работу и возвращает результат.
Главный агент оценивает результат и может поручить дальнейшую работу субагенту B.
Когда все части завершены, главный агент объединяет результаты.
Субагент A не обязательно знает, что делает субагент B. Коммуникация и обмен информацией координируются через главного агента.
Преимущество: централизованный контроль, более простое отслеживание состояния, более чёткая ответственность и меньший риск неконтролируемой коммуникации между агентами.
Недостаток: главный агент становится центральной точкой, через которую интерпретируются инструкции и результаты задач. Если при делегировании он опустит важную информацию, субагент может работать с неполным контекстом.
2. Peer-to-Peer – агенты общаются друг с другом
Второй подход предполагает прямую или непрерывную коммуникацию между агентами, например через общий поток беседы или систему сообщений (*Message Bus*).
Представьте такой сценарий:
Агент A пишет код и публикует событие CodeWritten.
Агент B, отвечающий за тестирование, получает событие и запускает тесты.
Агент C тем временем готовит документацию.
Агенты непрерывно обмениваются результатами и реагируют на изменения.
Преимущество: параллельное выполнение задач, быстрый обмен информацией и меньшая зависимость от одного центрального агента.
Недостаток: более сложная координация, риск работы с устаревшей информацией, конфликтующие изменения и большая сложность поиска первопричины ошибок.
Оба подхода могут быть чрезвычайно полезны.
Но ни один из них сам по себе не решает фундаментальную проблему.
У агента может быть идеально определённая задача, но без понимания реальной бизнес-логики системы он может создать технически правильное решение, которое неверно с точки зрения бизнеса.
Где возникают ошибки в агентных процессах?
AI - это не детерминированный компилятор, который напрямую переводит инструкции в исходный код. Языковая модель интерпретирует доступную информацию и генерирует решения на основе этого контекста.
Когда информации не хватает, она может делать неверные предположения. Когда доступная информация неполна или противоречива, она может выбрать неподходящий подход.
Рассмотрим типичный процесс для более крупной задачи.
Шаг 1 - Интерпретация prompt пользователя
Главный агент получает задачу и пытается понять запрошенное изменение.
На этом этапе он может упустить зависимость, неправильно понять ограничение или предположить то, что никогда не было сказано явно.
Шаг 2 - Создание инструкций для субагента
Главный агент создаёт более конкретное описание задачи. Он отбирает из исходного prompt информацию, которую считает релевантной.
Однако, если он не знает некоторых бизнес-правил, он не может правильно передать их дальше.
Шаг 3 - Реализация
Субагент получает инструкции, анализирует часть кодовой базы и выбирает стратегию реализации.
Он может написать синтаксически правильный, качественный код, непреднамеренно изменив поведение, которое должно было остаться прежним.
Шаг 4 - Оценка результата
Главный агент получает результат субагента, оценивает его и решает, завершена ли задача.
Но он по-прежнему может действовать в рамках тех же неполных предположений, что и раньше.
Шаг 5 - Тестирование и исправление ошибок
Далее следуют unit-тесты, интеграционные тесты, E2E-тесты, статический анализ и проверка документации.
Эти механизмы значительно повышают надёжность программного обеспечения, но у них есть ограничения.
Тест проверяет конкретное ожидаемое поведение. Если важное бизнес-правило отсутствует в спецификации тестов, реализация может пройти все тесты и при этом нарушить это правило.
А когда AI исправляет одну проблему, он может непреднамеренно затронуть другую часть системы.
Так возникает знакомый цикл:
Реализация → Тестирование → Исправление → Регрессия → Ещё тестирование → Ещё одно исправление.
Поэтому простое увеличение числа агентов или более частое повторение тестов автоматически не гарантирует правильного результата.
Почему ошибки могут накапливаться по цепочке агентов?
Рассмотрим упрощённую математическую модель.
Предположим, у нас три последовательных шага, каждый из которых гипотетически выполняется правильно с вероятностью 95%.
Если эти шаги независимы и все три должны пройти успешно, вероятность составляет:
0.95 × 0.95 × 0.95 = 0.8574
Это примерно 85,7% вероятности того, что все три шага пройдут успешно.
При десяти таких независимых шагах результат будет:
0.95¹⁰ ≈ 59,9%
Это иллюстративный расчёт, а не измеренный показатель успешности AI-агентов. В реальных системах ошибки не всегда независимы, механизмы проверки могут ловить ошибки, а отдельные шаги могут исправлять предыдущие сбои.
Тем не менее пример демонстрирует важный принцип:
Надёжность отдельных агентов автоматически не гарантирует надёжность всей цепочки.
Когда неполные инструкции многократно интерпретируются на каждом этапе, появляются дополнительные возможности для неверных решений.
Именно поэтому я считаю, что простого добавления новых агентов, тестов и механизмов проверки недостаточно.
Нужно изменить то, как AI получает информацию о самой системе.
Ключевое различие: тесты проверяют результаты, бизнес-логика определяет границы
Обычный подход к разработке с помощью AI - реактивный.
Вы формулируете требование, AI реализует решение, а затем тесты показывают, не сломалось ли что-то.
Это, безусловно, лучше, чем отсутствие тестов.
Но остаётся фундаментальная слабость:
Тесты не могут надёжно проверять бизнес-правила, о которых никто не знает и которые не входят в спецификацию тестов.
Поэтому я считаю, что лучший подход - дать AI информацию о реальном поведении системы до начала реализации.
Не только что нужно изменить, но и:
Какие бизнес-правила относятся к затрагиваемому коду.
Какие другие модули зависят от этой функциональности.
Какие входные и выходные данные должны остаться совместимыми.
Какие сценарии должны остаться неизменными.
Какие существуют исключения и исторические ограничения.
Какие части реализации AI может изменять, а какие должен сохранить.
Это значительно сокращает объём поведения, которое AI должен выводить самостоятельно.
Два подхода к одной и той же задаче
Подход A - Prompt + тестирование
AI получает задачу, выбирает реализацию на основе доступного контекста, создаёт решение и запускает тесты.
Если тесты неполны, нарушения существующих бизнес-правил могут остаться незамеченными.
Подход B - Prompt + бизнес-логика + тестирование
AI получает задачу вместе с релевантными правилами, зависимостями, контрактами и ограничениями.
В результате он знает, какое поведение нужно сохранить, ещё до начала реализации.
Тогда тесты не только обнаруживают ошибки. Они также проверяют конкретные бизнес-контракты.
Разница не в том, что мы перестаём тестировать.
Разница в том, что мы пытаемся предотвратить ошибки до того, как они появились.

Практический пример: добавление нового способа оплаты
Представьте, что у нас есть файл CheckoutService.ts, который обрабатывает платежи в приложении электронной коммерции.
Мы хотим добавить оплату картой как дополнительный способ оплаты.
Вариант A: обычный prompt
Задача:
> Добавь оплату картой в CheckoutService.ts. Сохрани существующую функциональность и запусти все тесты.
AI изменяет код, добавляет новую ветку оплаты и обновляет тесты.
Все тесты проходят.
Задача отмечена как выполненная.
Однако в системе есть важное бизнес-правило:
Корпоративные аккаунты должны использовать банковский перевод как способ оплаты по умолчанию.
Это правило было введено несколько лет назад. Разработчика, который его реализовал, в компании уже нет. Правило чётко не задокументировано, и отдельного регрессионного теста для него нет.
AI вводит оплату картой как способ по умолчанию для всех клиентов.
С точки зрения реализации новая функциональность работает правильно.
С точки зрения бизнес-логики система сломана.
А тесты проблему не обнаружили.
Вариант B: структурированная Task с бизнес-логикой в AITM
Теперь представьте, что AI получает тот же запрос, но на этот раз задача включает соответствующий бизнес-контракт, связанные переменные, ссылки на исторические задачи и точные границы разрешённых изменений.
Задача может выглядеть так:
READ CLAUDE.md first.
TASK:
Add card payment as an additional payment method
in CheckoutService.ts.
Contract:
%CHECKOUT-019 — "For company accounts
(companyId != null), bank transfer must remain
the default payment method. Card payment may
be offered only as an additional option."
Related variables:
BL.CHECKOUT.PAYMENTMETHOD_DEFAULT
BL.CHECKOUT.PAYMENTMETHOD_OPTIONS
Related task:
#<link to the task that originally implemented bank-transfer-as-default checkout>
In scope:
- Add a new "card" option to the available payment methods in CheckoutService.ts.
- Expose it as a selectable option in the existing payment method selection flow.
Out of scope:
- Changing the default payment method for any account type.
- Any UI/checkout-flow redesign beyond adding the new option.
- New payment provider integration logic beyond the method registration itself.
Must not break:
- Existing default payment selection logic (company accounts → bank transfer stays default).
- Company account checkout behavior end-to-end.
- Existing bank transfer processing path.
- Compatibility with the current payment API contract.
File path:
src/Services/CheckoutService.ts
Confirm the exact path via contractsForFile before editing.
Verify:
- Company account checkout still selects bank transfer by default
(companyId != null).
- Card payment appears as a selectable, non-default option.
- Existing bank transfer processing is unchanged.
- Run unit and integration tests covering CheckoutService.
Подробнее о том, как это работает в AITM: https://aitm.cz/Docs/KnowledgeSharing
Почему этот формат важен?
На первый взгляд это может выглядеть просто как более подробный prompt.
Но настоящее отличие в том, что задача связана с информацией, которую можно получить и проверить по реальному проекту.
1. Контракт %CHECKOUT-019
Идентификатор %CHECKOUT-019 - это не просто текстовая заметка.
Это иллюстративный идентификатор контракта, который агент может получить через GraphQL-операции, такие как contractsForFile или contractsForVariable.
Вместо того чтобы полагаться только на правило, записанное в prompt, агент может получить его структурированное представление и сверить с текущей кодовой базой.
2. Переменные бизнес-логики _BL.
Идентификаторы вроде _BL.CHECKOUT.PAYMENT_METHOD_DEFAULT и _BL.CHECKOUT.PAYMENT_METHOD_OPTIONS представляют бизнес-логику, выраженную через коммуникационный язык AITM.
Они помогают связать конкретное требование с правилами и переменными, определяющими поведение системы.
3. Ссылка на связанную задачу
Раздел Related task ссылается на исходную задачу, в которой было реализовано бизнес-правило.
Это даёт AI дополнительный контекст не только о том, как система ведёт себя сейчас, но и о том, почему могло быть принято то или иное решение.
4. Чётко определённые границы изменений
Разделы In scope, Out of scope и Must not break определяют три отдельные категории:
Что AI должен реализовать.
Что AI реализовывать не должен.
Какое существующее поведение AI должен сохранить.
Вместо того чтобы получить открытую задачу, которую можно свободно трактовать или расширять, AI получает точно определённый объём реализации.
5. Проверка перед написанием кода
Путь к файлу не считается автоматически верным.
Агенту предписано сначала использовать contractsForFile, подтвердить фактический путь и определить связанные контракты.
Только после этого он должен начинать изменять код.
6. Валидация prompt через TPV
Важная часть подхода AITM - валидатор prompt TPV.
Он проверяет обязательные разделы задачи до того, как она будет отправлена на выполнение.
Например, он проверяет наличие определения области работ, ограничений, контрактов, путей к файлам и требований к проверке.
Это переносит часть предотвращения ошибок с тестирования готового кода на подготовку самой задачи.
Примечание: идентификаторы контрактов и переменные бизнес-логики в этом примере - иллюстративные заглушки. В реальном проекте оптимизатор получает их через GraphQL из конкретного проекта. Их не следует угадывать или генерировать без проверки.
Что меняется при таком подходе?
При обычном подходе агент сначала интерпретирует открытую задачу и сам решает, какие файлы, зависимости и бизнес-правила важны.
В AITM задача связана с конкретными контрактами, переменными бизнес-логики, историческими задачами и чётко определёнными границами изменений.
Поэтому агент может принимать решения на основе проверяемой информации, а не опираться в первую очередь на предположения.
И именно здесь я вижу фундаментальное отличие.
Бизнес-логика перестаёт быть просто частью документации. Она становится частью самого процесса управления реализацией.
Это принцип, лежащий в основе AITM
Когда мы начинали проектировать AITM (AI Task Manager), мы не хотели создавать очередную систему, которая запускает агентов, распределяет задачи и потом проверяет их результаты.
Мы сосредоточились на другом вопросе:
Что если AI мог бы получать релевантную бизнес-логику прямо из существующего исходного кода, прежде чем вносить какие-либо изменения?
Не просто документацию, которую кто-то написал год назад.
Не просто общие инструкции, хранящиеся в skill.
И не просто несколько файлов, которые агент случайно выбрал.
А структурированную информацию, описывающую, как на самом деле ведёт себя затрагиваемая часть системы, какие контракты ею управляют и какие другие компоненты от неё зависят.
Поэтому основной принцип AITM - обогащать рабочий prompt бизнес-логикой, определённой по соответствующим частям кодовой базы.
Агент получает не только информацию о том, что он должен сделать, но и о том, что он должен сохранить.
Это особенно важно в крупных программных системах, где один prompt может не содержать всех релевантных зависимостей и ограничений.
Бизнес-логика как ограждения для AI
Представьте бизнес-логику как ограждения вдоль дороги.
Без ограждений AI может пойти по множеству разных путей. Одни приведут к правильному решению, другие нарушат скрытые правила системы.
Предоставляя релевантные контракты и ограничения, мы значительно сужаем пространство нежелательных решений.
AI по-прежнему может самостоятельно выбирать стратегии реализации, алгоритмы и структуру кода.
Но он обязан соблюдать известные бизнес-правила.
Последующее тестирование затем проверяет, действительно ли эти правила были сохранены.
Это фундаментальное изменение философии.
Мы пытаемся не просто исправлять ошибки, которые создаёт AI. Мы пытаемся снизить вероятность того, что эти ошибки вообще появятся.
Значит ли это, что агенты и тесты больше не нужны?
Ни в коем случае.
Агенты полезны для параллельного выполнения, специализированных видов деятельности и автоматизации больших задач.
Unit-тесты, интеграционные тесты и E2E-тесты остаются важнейшими компонентами обеспечения качества программного обеспечения.
Но оркестрация агентов и автоматизированное тестирование не могут заменить знание бизнес-логики.
Если агент не понимает, что система должна сохранить, даже идеально организованная команда субагентов не решит основную проблему.
А если тесты не покрывают релевантные сценарии, все тесты могут проходить, а приложение при этом будет вести себя неправильно с точки зрения бизнеса.
Правильный подход - не выбирать между бизнес-логикой и тестированием. Нужно их сочетать.
Сначала определить реальное поведение системы.
Затем выразить это поведение в виде чётких правил и контрактов.
Далее передать эти правила AI вместе с задачей.
И только после этого переходить к реализации, валидации и тестированию.
Такой подход может сократить количество лишних исправлений, регрессий и повторных циклов реализации.
Вывод: дело не в количестве агентов. Дело в качестве информации.
Для простых приложений AI может давать отличные результаты даже при относительно коротких инструкциях.
Но в корпоративном программном обеспечении с полумиллионом строк кода недостаточно предполагать, что агент всё поймёт правильно, найдёт каждую зависимость и затем безупречно протестирует собственную работу.
Чем больше система, тем важнее понимать и защищать её реальное бизнес-поведение.
У вас может быть десять идеально сотрудничающих агентов. Но если ни один из них не знает критически важного бизнес-правила, вместе они могут создать идеально протестированное решение, которое в корне неверно.
Поэтому с AITM мы выбираем другой подход.
Сначала контекст, правила и контракты.
Затем реализация.
И наконец валидация и тестирование.
Потому что цель не в том, чтобы AI написал как можно больше кода за кратчайшее время.
Цель в том, чтобы AI изменил ровно то, что нужно изменить, не сломав то, что уже работает.