Agentic SDD: как заставить нейросети писать код по жестким спецификациям
В проекте Findrates.ai подход Agentic SDD (автономная разработка через спецификации) работает каждый день: мы закрыли по этому конвейеру больше 240 планов. Наш реальный процесс сильно отличается от слайдов с конференций, где классический SDD преподносят как универсальное решение всех проблем.
Проблема вайбкодинга
С появлением LLM разработчики начали писать код через «вайбкодинг» (vibecoding) — просили чат-бота «сделай фичу X». Для простых скриптов и прототипов этого хватало. На боевой кодовой базе вайбкодинг быстро привел к потере контекста: модели забывали требования между сессиями, ломали соседние модули и плодили технический долг.
Чтобы вернуть контроль над архитектурой, команды начали вспоминать про Spec-Driven Development (SDD): сначала пишется спецификация в Markdown, которая фиксирует требования, а нейросеть в Cursor или Claude реализует её по шагам.
Почему канонический SDD ломается на практике
На бумаге схема выглядит логично: разработчик вручную пишет спецификацию, скармливает её агенту и нажимает «Apply».
На практике спецификация, написанная человеком или сгенерированная моделью в рамках одного чата, оторвана от реального состояния системы. Автор спеки неизбежно придумывает методы БД, которых нет в проекте, и забывает о контрактах соседних модулей. Когда нейросеть пишет код и сама же покрывает его тестами, она лишь подтверждает собственные ошибки. Начинается цикл fix -> error -> fix, а спецификация устаревает уже через два коммита.
Мы отказались от спецификаций «на доверии» и построили Agentic SDD — многоуровневый конвейер, где специализированные агенты сами готовят, перепроверяют и исполняют спецификацию на изолированных этапах.
Сравнение теории и продакшена:
| Параметр | Канонический SDD (в статьях) | Agentic SDD в Findrates.ai (в реальности) |
|---|---|---|
| Источник ценности | Готовое ТЗ от заказчика | Бэклог от бизнеса, продакта и операторов + фильтр Продюсера |
| Разведка | Код пишется с нуля или по догадкам | Оркестратор изолирует контекст в worktree и делит задачу на слайсы (<slug>-slices.md) |
| Критерии приемки | Пишет автор кода | Пишет независимый аналитик (агент Ольга) с Must-Not списками |
| Ревью плана | Ручной просмотр Markdown | Враждебное ревью от независимых LLM до полного устранения замечаний |
| Проверка (TDD) | Тесты пишутся после кода | Строгий BDD до реализации + мутационное тестирование (Stryker) |
| QA и Деплой | Ручная передача тестировщику | Автономный QA-цикл Марины: до 5 раундов fix -> retest (прод — только вручную) |
Фильтр ценности: защита от холостых прогонов
Полный цикл SDD — ресурсоемкий процесс. Прогон одного слайса требует $2–$6 в токенах API и занимает 15–25 минут работы моделей. Это дешевле часа работы сеньор-инженера, но если скармливать конвейеру задачи без приоритизации, бюджет уйдет впустую.
В Findrates.ai задачи поступают в ClickUp от Product Owner, бизнеса, операторов платформы и исследователей. Чтобы отсеять шум до запуска тяжелого пайплайна, работает агент-Продюсер (скилл producer).
До формирования спецификации Продюсер анализирует:
- Текущий бэклог.
- Цели релиза (MUST / SHOULD).
- Ошибки и выводы прошлых релизов (
retro.md). - Сигналы мониторинга и алерты из продакшена.
Продюсер оценивает продуктовый вес задач и отбирает Топ-5. Если задача не решает актуальную проблему платформы или пользователей, она не идет в работу.
Как формируется спецификация
Когда задача выбрана, Оркестратор не пытается написать спецификацию одним большим промптом. Он собирает исполняемый контракт через несколько изолированных шагов:
Имена агентов (Ольга, Ева, Марина) — это способ изоляции контекста и инструкций. Агент критериев не видит исходный код, чтобы не подгонять требования под реализацию (anti-anchoring), а агент QA не имеет доступа к коду бэкенда и тестирует систему как черный ящик.
1. Изоляция и декомпозиция (Slicing)
Оркестратор создает отдельный git worktree и делит фичу на независимые слайсы (plans/<feature-slug>-slices.md). Планируется только один атомарный инкремент за раз. Для багов действует строгое правило: агент Марина сначала воспроизводит проблему на текущей версии (Baseline Repro). Без подтвержденного красного e2e-теста исправление не пишется.
2. Разведка кодовой базы (Pre-plan Scout)
Скрипт в режиме read-only сканирует репозиторий: находит нужные файлы, импорты, типы данных и актуальные сигнатуры методов. План опирается на существующую структуру файлов, а не на предположения LLM.
3. Независимые критерии приемки (Агент Ольга)
Бизнес-аналитик формирует acceptance-criteria.md. Ольга формулирует позитивные сценарии и обязательные ограничения (Must-Not):
### Acceptance Criteria
- [ ] При смене валюты пересчитывать тариф по курсу ЦБ на дату создания заявки.
- [ ] Отображать индикатор валюты в карточке тарифа и таблице сравнения.
### Must-Not Invariants
- [ ] MUST NOT финализировать заявку со статусом EXPIRED.
- [ ] MUST NOT вызывать `recalculateTotal()` без проверки прав оператора.
4. UX-контракт (Агент Ева)
Для интерфейсных задач дизайнер Ева формирует контракт на основе дизайн-системы: фиксирует состояния (loading, empty, error, success), компоненты для переиспользования и требования к доступности.
5. Структурированный план (Tech-Lead)
Техлид собирает итоговый plan.md и разбивает его на фазы (phase-1.md, phase-2.md). Внутри плана нет готового кода — только алгоритмы, проверка зависимостей и архитектурные решения. Этот верифицированный документ и есть спецификация.
Обязательные разделы плана:
- Foundations: базовые сущности ядра, на которые опирается фича. Если сущности нет, создается запись в реестре техдолга.
- State Machine: если меняются статусы сущности, составляется таблица переходов
состояние × событие × guard-условие × запись в БД. - Слепое жюри (Blind Jury): для неочевидных архитектурных развилок генерируются 2–3 варианта без пометок автора и передаются независимому LLM-судье для выбора оптимального решения.
Все компромиссы фиксируются в decisions.md. Во время кодинга архитектурные решения не принимаются «на ходу».
От плана к коду и верификации
Автор плана не имеет права проводить его ревью.
Готовый план отправляется на проверку отдельной модели (Codex, Tencent Hunyuan 3 или Claude Opus). Модель ищет нестыковки в типах, вызовы несуществующих функций и пропущенные миграции БД. Работа блокируется до тех пор, пока ревьюер не подтвердит отсутствие замечаний.
Фрагмент отчета ревьюера codex-plan-review.log:
[CRITICAL] Фантомный метод БД в Phase 2.
Вызов `db.rates.updateStatus()` не существует в `src/db/rates.ts`.
Существующий метод требует явной передачи `tenantId`. План сломает сборку на шаге 3.
Только после согласования плана Оркестратор приступает к коду. Мы используем BDD (Behavior-Driven Development): тесты пишутся строго по спецификации до написания логики. Мутационное тестирование (Stryker) проверяет качество тестов — если изменение логики не приводит к падению тестов, сборка не принимается. После генерации кода гейт code-vs-plan сверяет реализацию с критериями Ольги.
Затем код разворачивается на локальном стейджинге. Агент Марина прогоняет e2e-сценарии через Telethon и Playwright. У конвейера есть лимит — 5 раундов исправления ошибок. Если за 5 попыток fix -> retest сценарии не проходят, пайплайн останавливается и отправляет алерт инженеру в Telegram.
По статистике 240+ закрытых планов:
- ~84% задач проходят конвейер полностью автономно до зеленого стейджинга.
- ~16% задач требуют ручного вмешательства (из-за скрытого техдолга, расхождений сторонних API или неполных требований в бэклоге).
Выкатка в прод всегда выполняется человеком вручную. Конвейер автоматизирует рутинную разработку и тестирование, оставляя контроль за релизом за инженером.
Итог
Разница между хаосом вайбкодинга и работающим конвейером сводится к одному правилу: никогда не позволять модели оценивать собственный результат.
Когда планирование изолировано в чистом worktree, критерии формирует независимый агент, а оппонирующая модель вычищает фантомные вызовы до первой строчки кода — Agentic SDD перестает быть теоретической концепцией и превращается в надежный инструмент, закрывающий сотни задач на автомате.