Дифференциальный анализ спецификаций
- title
- Дифференциальный анализ спецификаций
- type
- concept
- summary
- Собрать систему несколькими независимыми циклами агентов, сравнить готовые реализации и разобрать каждое расхождение как неучтённое решение.
- tags
- agentic-coding, software-engineering, spec-driven-development
- created
- 2026-07-21
- updated
- 2026-07-21
- lang
- ru
- translation_of
- differential-spec-analysis
- source_updated
- 2026-07-21
- translated
- 2026-09-01
- translator
- lllm/antigravity/gemini-3.7-flash-medium
Дифференциальный анализ спецификаций - это метод поиска пробелов в спецификации, основанный на том, что агенты достаточно дёшевы, чтобы собрать систему с нуля несколько раз. Запустите несколько независимых циклов агентов по одному и тому же заданию, дайте каждому подготовить полную реализацию, а затем сравните результаты. Везде, где они разойдутся, агент принял решение, которого не было в спецификации.
Название и практический пример принадлежат Josh Bleecher Snyder'у, который применил этот подход к распределённому DNS-серверу exe.dev в claude-is-not-a-compiler; отдельно он описал технику на commaok.xyz.
Наблюдение, лежащее в основе
Агенты задают вопросы. В циклах Bleecher Snyder'а они сыпались на всех уровнях - от общей структуры до конкретных строк кода, и ответы на них кажутся очевидным способом сделать спецификацию точнее.
Проблема в том, о чём они не спрашивают:
Поразительно, о скольких важных решениях агенты даже не спросили, а просто приняли их - причём по-разному.
Агент, который натыкается на неоднозначность и молча её разрешает, выдаёт рабочий код и не оставляет никаких следов своего выбора. Выявить такие места, читая одну реализацию, невозможно: в ней решение выглядит единственно возможным. Их находят сравнением - расхождение служит сигналом о том, что точка принятия решения вообще существовала.
Цикл работы
- Сначала согласовать общую стратегию и архитектуру силами людей. Это исходное задание; техника проверяет его, а не создаёт с нуля.
- Запустить несколько параллельных циклов агентов на создание всей системы целиком - включая тесты и состязательное код-ревью, а не просто черновик.
- Поручить новым агентам сравнить готовые реализации и выделить интересные расхождения. Сравнение - это тоже задача для агентов.
- Разобрать расхождения: поэкспериментировать, выбрать вариант и при необходимости откатить выбор, если он оказался неудачным.
- Зафиксировать каждое принятое решение в виде лаконичных письменных указаний.
- Выбросить все реализации и повторить.
Bleecher Snyder прогнал полный цикл трижды, прежде чем написать чистовой вариант, ссылаясь на Brooks'а ("планируйте выбросить одну версию: всё равно придётся") и Craig Zerouni ("если вы планируете выбросить одну версию, придётся выбросить две"). Суммарные затраты составили около недели внимания одного человека.
Что получается на выходе
Главный результат - это документ с указаниями, а не сами реализации. К третьему проходу его стало эмпирически достаточно, чтобы направить агента через ключевые решения: цели, архитектуру и отдельные низкоуровневые детали вроде точного типа данных для критически важного конкурентного кэша. "Эмпирически достаточно" здесь практический ориентир: спецификация готова, когда новый агент, следуя ей, перестаёт расходиться в важных для вас вещах.
Классический пример расхождения из кейса с DNS: репликация догоняет состояние, запрашивая все записи после последней известной, а затем переходит в long polling за новыми. Откаты баз данных случаются редко, но бывают, и они нарушают допущение об append-only, на котором держится вся схема. Опасность заметили все агенты; каждый агент обработал её по-своему. Выжившее решение помечает каждую строку случайно сгенерированным значением timeline, передаёт timeline крайней строки N в каждом запросе "записи после N" и считает несовпадение доказательством того, что история изменилась, после чего откатывается к полной чистой синхронизации.
Стилевые различия тоже проявляются: практической пользы в них меньше, но они не бесполезны. И Claude, и Codex сочли систему Claude'а более элегантной, а систему Codex'а - более дотошной.
Почему это работает
Неоднозначность в спецификации незаметна при одиночном чтении. Любой другой подход к поиску пробелов - внимательное ревью, чек-листы, просьбы к исполнителю отмечать неясности - зависит от того, заметит ли человек, что здесь вообще был выбор. Дифференциальный анализ не требует ничего замечать: он делает пробел механически наблюдаемым в виде diff'а. Плата за это - создание N систем вместо одной, но именно эту стоимость агенты свели к минимуму.
Логика здесь та же, что и в дифференциальном тестировании (запустить две реализации протокола друг против друга и исследовать расхождения), только перенесённая с поведения кода на инженерный замысел.
Ограничения
- Скоррелированные слепые зоны. У независимых циклов на базе одного семейства моделей общие априорные представления. Решение, в котором все агенты ошибутся одинаково, не создаст расхождений и останется невидимым. То, что Bleecher Snyder использовал и Claude, и Codex, отчасти сглаживает проблему.
- Расхождения не ранжируются. Diff показывает, что решение было принято, но не говорит, важно ли оно. Отделить сигнал от стилевого шума - работа человека, и именно она заняла у него неделю.
- Требуется настоящее задание. Если отправная точка слишком расплывчата, разойдётся вообще всё, и на выходе получится шум вместо списка решений.
- Предполагается, что вы можете позволить себе выбросить реализации. Это верно для изолированного внутреннего сервиса, но не столь очевидно для систем с миграциями, реальными данными или уже работающими пользователями.
Cross-references
- claude-is-not-a-compiler - первоисточник и кейс с DNS-сервером
- vibe-engineering - практика, которой служит эта техника
- llm-output-variance - базовая недетерминированность, которую метод не подавляет, а использует
- specsmaxxing, acceptance-criteria-ids - спецификация как главный артефакт, полученная другим путём
- log-distributed-llms - пессимистичный взгляд на разногласия нескольких агентов