From 8218a211b42a05a7fa6a7db5be55f653655170cd Mon Sep 17 00:00:00 2001 From: Dmitry Dementiev Date: Mon, 3 Aug 2026 22:08:08 +0300 Subject: [PATCH] =?UTF-8?q?refactor(skills):=20claude-subagent-playbook=20?= =?UTF-8?q?=E2=80=94=20=D1=81=D1=82=D0=B0=D1=80=D1=8B=D0=B5=20=D1=83=D1=80?= =?UTF-8?q?=D0=BE=D0=BA=D0=B8=20=D0=B2=D1=8B=D0=BD=D0=B5=D1=81=D0=B5=D0=BD?= =?UTF-8?q?=D1=8B=20=D0=B2=20=D0=B0=D1=80=D1=85=D0=B8=D0=B2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Зачем: - lessons.md вырос до 830 строк, и записи до рефакторинга 31 июля описывают другую редакцию скилла — прежнюю эффорт-карту, другой состав ролей, заготовку adversarial-reviewer, которой больше нет. - Что: - записи с 2026-07-06 по «казусы координации» 2026-07-31 перенесены в references/lessons-archive.md без изменений; живой файл сократился с 830 до 300 строк. - шапка lessons.md объясняет разрез и как двигать границу дальше; архив вне пути чтения прогона, ссылка на него только из lessons.md. - три указателя на переехавшие записи переведены на архив: казус форвардера в SKILL.md и codex-exec.md, sandbox-инцидент в codex-sandbox-apparmor.md. - Проверка: - все markdown-ссылки скилла разрешаются в существующие файлы. --- .../skills/claude-subagent-playbook/SKILL.md | 2 +- .../references/codex-exec.md | 3 +- .../references/codex-sandbox-apparmor.md | 2 +- .../references/lessons-archive.md | 547 +++++++++++++++++ .../references/lessons.md | 553 +----------------- 5 files changed, 563 insertions(+), 544 deletions(-) create mode 100644 agents/.agents/skills/claude-subagent-playbook/references/lessons-archive.md diff --git a/agents/.agents/skills/claude-subagent-playbook/SKILL.md b/agents/.agents/skills/claude-subagent-playbook/SKILL.md index 9b5783b..e084bf9 100644 --- a/agents/.agents/skills/claude-subagent-playbook/SKILL.md +++ b/agents/.agents/skills/claude-subagent-playbook/SKILL.md @@ -166,7 +166,7 @@ description: >- будит по завершении; рецепты, ветки и ловушки — [references/codex-exec.md](references/codex-exec.md). Пока исполнитель пишет — дерево его («Пределы параллельности»; казус - форвардера — в [references/lessons.md](references/lessons.md)). + форвардера — в [lessons-archive.md](references/lessons-archive.md)). После отчёта — **саморевью тем же тредом** (resume, effort medium; файл готов в `prompts/`): исполнитель проходит свой diff против критериев как ревьюер и сам чинит diff --git a/agents/.agents/skills/claude-subagent-playbook/references/codex-exec.md b/agents/.agents/skills/claude-subagent-playbook/references/codex-exec.md index bcdf833..16206bb 100644 --- a/agents/.agents/skills/claude-subagent-playbook/references/codex-exec.md +++ b/agents/.agents/skills/claude-subagent-playbook/references/codex-exec.md @@ -171,7 +171,8 @@ cat "$D/fix-prompt.md" | codex exec resume --json \ чем показывать оркестратору. Тогда раннеру (`fast-worker`; нет в репозитории — `general-purpose`) отдай **готовую команду** и правила разбора — не постановку задачи: тонкий агент, -получив постановку, реализует её сам (казус форвардера, lessons 2026-07-06). +получив постановку, реализует её сам (казус форвардера, lessons-archive +2026-07-06). Свой 10-минутный потолок на синхронный Bash раннер обходит отслеживаемым ожиданием: команда запускается его собственным фоновым Bash, а ждёт он процессом-ожидателем (`until grep -q '<маркер>' лог; do sleep 30; done` под diff --git a/agents/.agents/skills/claude-subagent-playbook/references/codex-sandbox-apparmor.md b/agents/.agents/skills/claude-subagent-playbook/references/codex-sandbox-apparmor.md index 62f8ce5..655caca 100644 --- a/agents/.agents/skills/claude-subagent-playbook/references/codex-sandbox-apparmor.md +++ b/agents/.agents/skills/claude-subagent-playbook/references/codex-sandbox-apparmor.md @@ -117,4 +117,4 @@ Ubuntu 24.04; там сжатая версия жила в codex-companion.md, линии уже поглощён codex-exec.md). Сжатая версия урока здесь — в [codex-exec.md](codex-exec.md), сквозное правило «Linux: sandbox может молча сломаться обновлением Codex»; датированная запись — в -[lessons.md](lessons.md). +[lessons-archive.md](lessons-archive.md). diff --git a/agents/.agents/skills/claude-subagent-playbook/references/lessons-archive.md b/agents/.agents/skills/claude-subagent-playbook/references/lessons-archive.md new file mode 100644 index 0000000..ab0c734 --- /dev/null +++ b/agents/.agents/skills/claude-subagent-playbook/references/lessons-archive.md @@ -0,0 +1,547 @@ +# Эмпирика прогонов — архив по 2026-07-31 + +Записи с первого прогона по структурный рефакторинг 31 июля 2026 +(коммит `3e0498e`). Они описывают предыдущую редакцию скилла: другую +эффорт-карту, другой состав ролей, заготовку `adversarial-reviewer`, +которой больше нет. Держим ради родословной решений — что когда поймал +конвейер и почему правило появилось. + +В пути чтения прогона этого файла нет: на него ссылается только +[lessons.md](lessons.md). Живые хвосты этих записей сведены там же в +очередь на механизм — запись 2026-08-03. + +## 2026-07-06 — t2-ml-forecast, задача 05 (первый прогон; дистиллировано 2026-07-12) + +- Свежий взгляд на постановку окупился: блокер name_ru (в данных — английский), + две «одностроки» с проектными решениями, дыра регенерации `.ipynb`. + Поглощено: SKILL.md этап 2. +- Казус форвардера: субагент, получив постановку вместо команды, реализовал + задачу сам (+1227 строк). Поглощено: SKILL.md этап 3, codex-exec (раннер). +- Слепое двойное ревью: пересечение находок — ноль; Клод подтвердил математику + и артефакты, Codex нашёл две дыры в тестах. Поглощено: SKILL.md (роли). +- Смерть фонового ревьюера без доставленного отчёта; транскрипт не спас. + Поглощено: SKILL.md этап 4 (вердикт — файлом, сообщение — указателем). +- Цифры: ревью постановки ~60k токенов; конвейер ~3 часа, реализация ~20 мин. + +## 2026-07-07 — наглядность витрины (полный конвейер; дистиллировано 2026-07-12) + +- Idle-уведомление ≠ отчёт; голый поллер вне run_in_background умирает при + смене хода; статус job — не истина (зомби «running» после смерти воркера: + истина — mtime артефакта + лог + pgrep). Поглощено: SKILL.md + («Пользователь в петле»), codex-exec (фоновый запуск, раннер). +- Безадресный resume подхватывает чужой тред. Поглощено: codex-exec. +- Доводы отклонений — в файл задачи (свежий тред продолжает без контекста + предшественника). Отменено 2026-07-19: доводы — в файл отчёта триажа, + свежий тред получает его путём; тикет в триаже не правится (эхо файла + задачи, прогон 13). Поглощено: prompts/triage-header.md, SKILL.md 5–6. +- Не поглощено (держать в уме при постановке): правила задачи ранжировать + явно («правило A главнее буквы E») — внутренние противоречия всплывают + после починки. +- Цифры: реализация 18 мин; триаж ~8 мин; тесты 147 -> 154. + +## 2026-07-09 — local-transcriber, SendTo (первый под Windows; дистиллировано 2026-07-12) + +- Git Bash-стек работает целиком; классификатор режет companion `--write`, + прямой `codex exec` проходит. Поглощено: codex-exec. +- Свежий взгляд: 2 major (OEM-кодировка `.cmd` на кириллическом профиле, + протухание пути venv) + load-bearing порядок проверок. Поглощено: этап 2. +- Отписка: вердикт одной строкой, проверка по JSONL подтвердила работу. + Поглощено: SKILL.md этап 4, codex-exec. +- Эмпирический ревьюер (воспроизведение краевых случаев вне репо) — вердикт + твёрже. Поглощено: SKILL.md этап 4, boilerplate шаблонов. +- Цифры: ревью постановки ~57k, кода ~48k, перепроверка ~45k токенов. + +## 2026-07-10 — четыре записи (дистиллировано 2026-07-12) + +- Ревьюер Codex без read-only: мандат промптом надёжен, песочница не режется. + Поглощено: codex-exec (ветка ревьюера). +- Sandbox-инцидент CLI 0.144.1 (bwrap+userns vs AppArmor) и ловушка memfd + (профиль на путь bwrap не цепляется — вешать на бинарь codex). Поглощено: + codex-exec + codex-sandbox-apparmor.md. +- Постановка через `/to-tickets` ложится в конвейер без трения; двойное + слепое ревью постановки окупилось (Клод — механика кода, Codex — уровень + требований; пересечение 2 из ~15). Поглощено: SKILL.md этапы 1–2. +- Ретро расхода контекста (3 цикла): находки проходили через оркестратора + до шести раз; review-промпт дублировался; ~7 пустых ходов на idle-пингах. + Поглощено: SKILL.md (роль оркестратора: индекс, cat, файлы), шаблоны. + +## Прогон 2026-07-12: clickstream-demo, задача 20 — флаки runtime-гейта + +Полный конвейер + три захода стендовой приёмки. Главный урок прогона: +**ревью по чтению кода не заменяет сквозный прогон** — два класса дефектов +вскрылись только на стенде. + +**Что поймал каждый этап:** +- Ревью постановки (Opus): настоящий корень — отсутствие SIGTERM-хендлера + (python PID 1, SIGKILL после grace); один из двух вариантов фикса в + постановке гонку не закрывал. Плюс критерий «красный сценарий всё ещё + ловится» и запрет вероятностных смягчений. +- Слепые ревью: Codex — grace-период 10с и обходимость precheck (пара из + старой backfill-строки); Клод — подтвердил структурный довод, на узкой + перепроверке принёс НОВУЮ находку (тест биндил порт 9109 — флаки 1/13). + Пересечение — 2 темы из ~8 (grace, слабый контракт-тест): не «стабильно + ноль», но малое; обе родословные оправдались. +- Стендовая приёмка (3 захода): (1) гейт годами жил на побочном эффекте + бага — пересекающие визиты давала «нелегальная переработка» генератора + после игнорируемого SIGTERM; честный фикс оставил проверку без сырья; + (2) таймзона: наивные метки STG (UTC) против границы с `+00:00` на + сервере Europe/Moscow — precheck был зелёным вакуумно; та же ошибка — в + приёмочном скрипте координатора (наивная конвенция DDS). Урок: сравнение + времени в SQL — только с явным поясом с обеих сторон. + +**Ретро контекста оркестратора** (главный пожиратель — внеплановые циклы): +диагнозы падений приёмки велись мастером инлайн (~15 вызовов); boilerplate +промптов переписывался трижды; обменные файлы шли кириллицей (×1,5–2); +правки задачи-файла — тремя крупными Edit (old+new = двойной текст); +промпты будильников пересказывали план. Поглощено 2026-07-12: SKILL.md +(принцип «мастер решает — субагенты выясняют», стоп-кран «сам — максимум +один заход», механика — fast-worker'у, обменные файлы на английском, +будильник одной строкой, сквозная проверка до ревью, фолбэк ревьюера +deep-reasoner — обкатан этим прогоном), prompt-templates + prompts/ +(готовые boilerplate-файлы, английские скелеты), codex-exec (модель +gpt-5.6-sol, medium для узких починок, ловушка `&`). Слепое Fable-ревью +самого скилла (по глоссарию writing-great-skills): восстановление после +rm -rf подтверждено без потерь, 9 MINOR + 5 NIT согласованности — все +закрыты тем же днём. + +**Прочее:** казус двойного фона (`&` при run_in_background) — спасён +ожидателем `kill -0`; принятие остаточного риска (публикация не ограничена +по времени) зафиксировано доводом в задаче — паттерн «риск принят + после +фикса такой отказ падает громко и честно» работает как аргумент приёмки. +Отдельный казус координатора: `rm -rf` «зеркала» скилла прошёл сквозь +симлинк `~/.claude/skills -> dotfiles` и снёс оригинал; восстановлено из +git (`git show HEAD:path`) + повторным наложением правок из контекста. +Урок: перед rm — `ls -la` цели и родителя, симлинк-родитель = чужая +территория. + +**Цифры:** реализация ~25 мин; ревью постановки 75k токенов субагента, +ревью кода 65k, перепроверка 80k (с новой находкой); приёмка — 4 прогона +гейта по ~1,5 мин + красный сценарий; тесты 190 -> 192 + 21. + +## Прогон 2026-07-12/13: clickstream-demo, задача 13 — глагол next-day + +Первый прогон после поглощения уроков задачи 20 — они сработали: вердикты +читались по одному разу, boilerplate не переписывался (cat из prompts/), +обмен на английском, ноль инлайн-диагнозов мастера (стоп-кран держит), +будильники одной строкой (9 взводов, ни один не сработал впустую — все +сняты по уведомлениям). + +**Что поймал каждый этап:** +- Двойное ревью постановки: пересечение 5 тем из ~15 (guard, идемпотентность, + атомарность, формат цепочки, проверки). Уникальное: Клод — «next-day = + новый режим запуска, постановка прячет основную работу за словом + „переиспользует"»; Codex — «расписание запустит дефолтный backfill» + (скоуп-решение: расписание вынесено отдельной задачей). +- Слепые ревью кода: пересечение 1 тема из ~12 (нулевой стык). Codex — + дефекты нового скрипта (хвост за границей, TZ), Клод — архитектура + (retention Kafka против пересборки счётчиков — блокер будущей задачи, + скрытая связка наборов настроек). Родословные разошлись почти полностью. +- Эмпирика исполнителя: требование обоих ревью («громкий отказ на нулевом + стыке») покраснело на честном стенде — ночной провал трафика, снова класс + «артефакт верификатора». Диагноз по данным делегирован исполнителю тем же + тредом (state на границе: 0 активных визитов — restore ни при чём). + Урок: требование ревьюеров сверяй с критериями приёмки и реальным + распределением данных, прежде чем принять его в код. +- Узкая перепроверка Codex снова принесла новый MAJOR (микросекунды в + UTC-нормализации) — второй прогон подряд, считать штатным режимом. + +**Новые пожиратели контекста мастера, по убыванию:** +1. Эхо файла задачи: исполнитель дописал резолюции в тикет, который мастер + сам писал на этапе 2, — харнесс вкатил в контекст все ~190 строк; итого + текст тикета прошёл через мастера трижды (Write + эхо + финальное + чтение). Не поглощено; митигация неочевидна — резолюции проекту нужны + именно в тикете. Держать в уме при выборе, кто пишет файл задачи. +2. Клод-ревьюер держит формат индекса хуже Codex: многострочные находки и + развёрнутые confirmations при жёстком boilerplate («one-phrase essence»). + Поглощено: обёртка Клод-ревьюера в prompt-templates дополнена + напоминанием об однострочности. +3. Авторство решений этапа 2 — у мастера по определению (110 строк + кириллицы в тикет после двойного ревью постановки): это цена этапа, на + мелких задачах конвейер не разворачивать (правило уже в SKILL.md, + теперь с ценником). + +Дешёвый приём: вердикт перепроверки Клода взят из строки task-notification +(обёртка требует финальным актом только VERDICT-строку) — файл не читался. + +**Цифры:** конвейер ~2 часа от ревью постановки до приёмки; реализация +~30 мин; Клод-субагенты: ревью постановки 94k, кода 108k, перепроверка +126k токенов; Codex-ревью: 42/36 команд; 2 круга триажа + узкий диагноз; +тесты 192 -> 204 + 21 -> 31; учебный цикл: DM 322 -> 10 026 -> 19 196 за +два next-day. + +## Прогон 2026-07-13: t2-presale, тикет 06 — совместимость со средой стенда + +**Главный урок — информирование пользователя.** Статусы на границах этапов +были телеграфными и в терминах плейбука («этап 4», «триаж», «узкая +перепроверка»); эпизодически заглядывающий пользователь потерял нить: +спросил «мы остановились?» при живом фоне, а после финала считал, что +конвейер ещё на ревью постановки и «решение удалили». Фидбек дословно: +«информирование о ходе процесса было очень скудным». Урок: на каждой +границе — карта прогресса 4–7 строк (✅ сделано / ▶ идёт / ⬜ дальше) +обычными словами, термины плейбука только с расшифровкой; карта дополняет +содержательную сводку, не заменяет. Поглощено 2026-07-23: SKILL.md +(«Пользователь в петле») и близнец codex-subagent-playbook +(«Партнёр в петле»). + +**Что поймал каждый этап:** +- Ревью постановки с эмпирикой перекроило тикет до реализации: Codex из + контейнера установил, что во внутренних зеркалах duckdb нет вовсе + (BLOCKER → план Б wheel'ом с публичного PyPI) и что названный в тикете + кандидат convert_dtypes теряет точность через float64 — исполнитель + сразу пошёл верным путём. +- Фактическое противоречие ревьюеров (верхний cp37-wheel duckdb: «0.10.3» + у Клода против «1.2.2» у Codex) оркестратор снял ОДНОЙ контрольной + командой (`pip download` в контейнере) до триажа — дёшево, а от факта + зависел пин. Приём: конфликт фактов — контрольный эксперимент, не + голосование. +- Слепые ревью кода: пересечение БОЛЬШОЕ (одна корневая тема — регрессии + нового вывода типов против старого пути: int64-переполнение роняло + загрузку, пробелы, BOOLEAN, inf). Контрпример к «пересечение ~ноль»: + когда правка замещает хорошо определённое старое поведение, обе + родословные сходятся на охоте за регрессиями — и это признак качества + находок, а не растраты. +- Перепроверка снова принесла хвост (смесь конечных с inf/-inf — DOUBLE): + третий прогон подряд, подтверждён штатный режим. + +**Прочее:** сетевые шаги с доступами пользователя (docker login/pull) +координировались `!`-командой в чат — работает без трения. Первый полный +прогон на gpt-5.6-sol как боевой модели — пользователь подтвердил цену, +качество исполнителя и ревьюера без нареканий. + +**Цифры:** постановка + двойное ревью постановки ~1 ч; реализация ~25 мин; +2 круга триажа + 2 узкие перепроверки; тесты 36 → 45 → 46, зелёные в двух +средах (современная + vendor-контейнер py3.7); приёмка оркестратора — оба +прогона своими руками. + +**Модели (датированная эволюция, к прогону 2026-07-13):** +- Урок о скоропортящихся фактах: 2026-07-10 утечка gpt-5.6-sol из конфига + считалась казусом («фронтир = дорогие лимиты»), 2026-07-13 пользователь + переоценил — Sol умная и относительно недорогая, теперь боевой дефолт. + Правило «модель явно, из конфига не наследовать» выжило, но по другой + причине: воспроизводимость, а не цена. Факты о ценах/лимитах моделей — + датировать и перепроверять у пользователя, не тащить из прошлых сессий + как вечную истину. +- Effort medium на узких контурах подтверждён боем: круг починки одной + находки и финальная перепроверка — чисто и быстрее high (до этого + правило в codex-exec было гипотезой). +- Роли от пользователя (2026-07-13): Опус — вкус и архитектура; Codex — + исполнитель (лучше и дешевле); исследование — паритет, Codex дешевле. + Кандидат на поглощение в SKILL.md (раздел «Роли»). +- НЕ ОБКАТАНО (рыночная наводка из обзоров, 2026-07-13): gpt-5.6-terra + medium/high для кода — на medium вдвое дешевле Sol на простых задачах + при том же уровне, сильно лучше Sonnet; минусы — ощутимо дольше запуск и + накладные на внешнюю оркестрацию. Вывод на сейчас: лимиты Codex у + пользователя не узкое место, менять нечего; потенциальная полоса — + bulk-механика /coordinator-loop и узкие починки, если лимиты станут + узкими. Проверка — один A/B на реальной узкой починке. + +## Прогоны 2026-07-20/21: headless-xray-proxy, задачи 03–04 — эксперимент «реализация на medium» + +- Дизайн: реализация Codex на `medium` (03 — жизненный цикл процессов, + 04 — проверяемая установка), остальное по правилам 2026-07-19; baseline — + задача 06 на high (1 MAJOR + 1 NIT от слепых ревью). +- Качество: 03 → 4 MAJOR (все — гонки конкурентности/восстановления), + 04 → 2 MAJOR, из них один (CODE-1) — дефект ПОСТАНОВКИ, не исполнителя. + Конвейер всё выловил и починил; «чистых» MAJOR реализации в 04 — один, + на уровне baseline. +- Экономика: 03 дешевле baseline (~636k+77k против ~735k+97k свежих + Codex-токенов), 04 — ДОРОЖЕ (~822k+135k): экономию реализации съел + триаж семи находок. Урок: экономию эффорта считать по конвейеру целиком. +- Казус CODE-1: spec-review на high уверенно выдумал несуществующий + однострочный формат `SHA256=` в `.dgst` (реальный — четыре записи + `MD5=`/`SHA1=`/`SHA2-256=`/`SHA2-512=`); дефект уехал в тикет и код, + пойман только слепым CODE-ревью, стоил поправки тикета до триажа. + Урок: внешние факты (форматы артефактов, версии релизов) эффортом не + лечатся — проверять реальным скачиванием/фикстурой из первоисточника. +- Эмпирика кэша Codex: смена `model_reasoning_effort` high→medium при + `resume` кэш треда не сбрасывает (~93–94% кэша во всех трёх задачах). +- Казусы харнеса: рестарт сессии дважды убивал фоновый codex — тред + спасался по сохранённому thread_id; `codex exec resume` принимает + ТОЛЬКО `-c`-оверрайды (`-s`/`-m`/`-o` → exit 2); usage убитого хода + теряется (нет `turn.completed`) — фиксировать с оговоркой из resume-хода. +- Решения пользователя 2026-07-21 (поглощено: codex-exec.md — эффорт, + SKILL.md — эффорт-карта Claude-субагентов): реализация по + отревьюированному тикету → medium допустим; Claude-субагентам effort + задавать явно — xhigh постановки/планы, high слепое ревью, medium + перепроверки; ревью ниже high не опускать. **Пересмотрено 2026-07-26** + (см. ниже) — карта сдвинута на ступень вниз под Opus 5. + +## Прогон 2026-07-21: yantar-dags, предразметка — этап постановки + +- Issues в GitLab созданы по конвенции репозитория, но мимо критериев + `/to-tickets`: без критериев приёмки чекбоксами, один тикет — два среза + (две разные точки стендовой проверки). Поймал пользователь сверкой ПОСЛЕ + публикации. Урок: сверка разбиения — до публикации, внутри `/to-tickets`. +- Пользователь заметил избыточность: текст тикета проходил через мастера + трижды (создание + проверка после создания + тщательное ревью перед + выполнением) — по времени и токенам. Поглощено 2026-07-21: SKILL.md + этапы 1–2 — `/to-tickets` как норма разбиения с меркой «тикет берётся в + свежей сессии без общего контекста»; правило «одно ревью на версию + артефакта» (сверка с пользователем = первая линия); шкала риска этапа 2 + (срез по принятой спеке без новых решений — внешнюю линию пропустить с + одной фразой обоснования). + +## Прогон 2026-07-22: clickstream-demo, issue #5 — счётчики стартовой истории + +Полный конвейер (исполнитель → два слепых ревью → триаж → узкая +перепроверка → стендовая приёмка) дошёл до цели, но шёл под ЧУЖИМ скиллом: +вместо этого плейбука вызван codex-subagent-playbook — близнец для +координатора на стороне Codex, на тот момент единственный из пары видимый +модели для автовызова. Отсюда главный казус: канал запуска Codex +«унаследовался» из handoff — конвейер пошёл через плагин-обёртку вопреки +codex-exec.md и воспроизвёл её известные баги (ложный «started» с подменой +ответа — issue #158, потерянные уведомления, несбрасываемый статус +остановленной задачи, read-only песочница ревьюера — вердикт извлекали из +лога задачи). Спас файловый контроль: мандаты и отчёты жили в `$SCRATCH`, +дерево сверялось тестами. Поглощено 2026-07-23: близнецу поставлен +`disable-model-invocation` и адресное описание («со стороны Claude Code — +claude-subagent-playbook»); правила канала в codex-exec.md были и остаются +действующим договором. + +Казус двух исполнителей: молчащего исполнителя заменили свежим без +остановки прежнего — в одном дереве оказались два писателя, дерево +пришлось перепроверять тестами. Поглощено: «Сбои координации» (владение — +только после остановки прежнего владельца). + +Казус приёмки: сценарий стендовой приёмки трижды падал на непроверенных +командах (способ аутентификации Airflow, маскировка кода выхода, имя +колонки витрины), а инлайн-python с экранированием в heredoc сломался и +после проверки. Поглощено: SKILL.md этап 6 (команды нового сценария — на +живом объекте до полного прогона, сложные вставки — файлами). Попутно: +`pkill -f` в одной команде с запуском/ожиданием находит шаблон в +собственной командной строке и убивает свой же Bash — дисциплина фоновых +процессов зафиксирована в памяти проекта. + +**Цифры:** триаж закрыл обе находки ревью (фрагментация наборов ID сняла +потолок Kafka: манифест 3 152 байта вместо ~0,81 МБ); приёмка — плоское +время next-day 716/718/716 с, мир 3 → 6 дней, 561 942 события; тесты +216 + 31 зелёные. + +## 2026-07-23: сверка близнецов после промаха скиллом + +В кодексовый близнец перенесены проверенные здешними прогонами правила: +одно ревью на версию артефакта, саморевью исполнителя и сквозная проверка +до внешних линий, цена тихой ошибки как критерий уровня, проверка внешних +фактов первоисточником, партнёр в петле. Обратно взяты «Пределы +параллельности» (глубина один; второй обзор ради отдельной линии, а не +свободного слота) — в SKILL.md, раздел «Роли». Скилл переведён на +автовызов моделью (описание с триггерами), близнец скрыт +`disable-model-invocation` — пара промахов исключена с обеих сторон. + +## 2026-07-23: taste-слепота триажа — «закрыть находку тестом» + +Прогон course-labs-redesign (issue #7, docs-only). Codex на триаже закрыл +9 из 10 находок честно, но каждую сопроводил контрактным тестом с +дословной цитатой учебной прозы (+7 хрупких тестов в +test_world_dags_contract.py: «не сравнивай», «днём 5» и т.п.). Формально +безупречно — «regression-тест на находку», по сути мусор: прибитая фраза +падает при любом честном рерайте текста, а не при дефекте. Обе линии +слепого ревью прошли раньше триажа и этого видеть не могли; поймал +пользователь, читая незакоммиченный дифф. + +Решения пользователя (перенесены в память проекта: +claude-reviews-code-meaningfulness): 1) в линзу Claude-ревьюера добавлять +осмысленность кода — «заслуживает ли существования каждый добавленный +артефакт», не только соответствие постановке; 2) срезание/переписывание +бессмысленного кода поручать Опусу, не Codex («у него куда лучше вкус»). +Механика: узкую перепроверку после триажа давать той линзе, что видит +дифф триажа целиком, — иначе taste-дефекты триажа не увидит никто. + +Попутно: образец заражает — исполнитель добавлял прозаические тесты, +следуя уже существующим в файле (жанр «тест на фразу README» там был до +него). Чистка легаси-жанра — отдельным issue (#24), не в ветке фичи. + +## Решение пользователя 2026-07-26: эффорт-карта Claude-субагентов под Opus 5 + +Скилл писался под Opus 4.8; у Opus 5 усилия распределены иначе, и `high` +стал верхней рабочей ступенью — выше неё смысл появляется редко. Карта в +SKILL.md сдвинута на ступень вниз: `high` — ревью постановок и планов +(было `xhigh`); `medium` — слепое ревью (было `high`) и узкие +перепроверки; default — механика. Нижняя граница ревью опущена с `high` +до `medium`. + +Сдвиг неравномерный (оценка пользователя, заведомо условная): `high` у +Opus 5 по отдаче ближе к прежнему `xhigh`, а `medium` — чуть ниже +прежнего `high`. То есть на ревью постановок потеря близка к нулю, а на +слепом ревью просадка есть, но меньше, чем выглядит по названию ступени. + +Следствие: ступеней теперь меньше, чем этапов, — слепое ревью и узкие +перепроверки делят `medium`. Это осознанно: эффорт задаёт лишь потолок +глубины поверх выбранной модели, тонкая настройка идёт промптом. + +`deep-reasoner` остаётся на `high` (решение пользователя): понижать +специалиста по рассуждению не надо. В роли фолбэк-ревьюера он приедет +ступенью выше карты — принято осознанно, карта задаёт минимум для роли, +а не потолок для агента. + +Оси не путать: механика едет на Sonnet (`fast-worker`, модель пришита в +определении), и ярус «default» там означает «эффорт не крутить», а не +дешёвый режим Опуса. + +Не изменилось: эффорт Codex (`references/codex-exec.md`) — там своя +шкала, по сложности; запрет менять effort между резюмами одного треда; и +главный предел — от уверенной выдумки внешних фактов не страхует никакой +эффорт (казус CODE-1). + +### Открытый вопрос 2026-07-26 — закрыт 2026-07-31 + +Проверено по схеме Agent-тула: ручки `effort` у него нет — ступень +задаётся только `effort:` во фронтматтере определения агента или +`opts.effort` в Workflow. Поглощено рефакторингом 2026-07-31: карта в +SKILL.md переписана на определения, в claude-agents.md добавлена +заготовка `adversarial-reviewer` (opus, medium), фолбэк «скептический +general-purpose» снят. + +### 2026-07-30: классификатор авторежима блокирует `-s danger-full-access` + +На запуске Codex-исполнителя (прогон тикета #12, кластер ClickHouse) +классификатор авторежима Claude Code заблокировал команду с +`-s danger-full-access`. Рабочая замена — не полный доступ, а песочница +с поштучной эскалацией: + +``` +-s workspace-write \ + -c 'approval_policy="on-request"' \ + -c 'approvals_reviewer="auto_review"' +``` + +Команда, которую песочница не пустила (docker и т.п.), эскалируется, и +авто-ревьюер Codex её одобряет — запуск уходит мимо песочницы штатно. + +Почему это лучше, а не просто обход: привилегия меньше («всё разрешено +заранее» → «поштучно и в логе»), и на приёмке можно посмотреть, какие +именно команды прошли мимо песочницы, — с полным доступом такого списка +не существует. Оговорка: `auto_review` делает песочницу совещательной — +эскалации одобряет автоматика самого Codex, поэтому мандат «исходники +вне ветки не трогать, окружение не ломать» по-прежнему держится на +промпте, не на песочнице (см. правило в SKILL.md). + +Классификатор при этом не враг: по отзывам сообщества, именно он в +авторежиме иногда спасает данные от разрушительных команд. Считать его +подсказкой «сузь привилегию», а не препятствием, которое надо обойти. + +Дополнение по итогам прогона (тот же день): рецепт исполнителя в +`codex-exec.md` штатную связку уже содержал — `danger-full-access` был +отступлением сессии-оркестратора «на всякий случай» под docker. Прогон +подтвердил, что запас не нужен: под штатной связкой у Codex прошли и +сеть (`docker manifest inspect`), и docker-сокет (`make up`, `docker +compose down`); отдельных событий эскалации в `--json`-логе нет — +успешные команды выглядят обычными `completed`. Кавеаты в +`codex-exec.md` обновлены, пометка «боем не обкатано» снята. + +## 2026-07-31: решение о вкусовой линзе неделю не доезжало до механизма + +Прогон clickstream-data-platform, тикет #18 (пробные DAG в Airflow). +Решение 2026-07-23 («в линзу Клод-ревьюера — осмысленность кода») жило в +записи уроков и в памяти ТОГО проекта, но в `prompts/`/`prompt-templates.md` +не попало. Оркестратор собрал линию TASK `cat`'ом из заготовки — и ревьюер +не был обязан спрашивать «не дичь ли это». Пользователь заметил это сам, +по ходу прогона, дословно: «Бывает когда сделано формально правильно, а по +сути - дичь». + +Урок общий: решение, записанное только в уроки, следующим прогоном не +исполняется. Память пообъектная — в другой репозиторий она не едет; ехать +может лишь механизм, который подшивается в промпт. Поглощено 2026-07-31: +`prompt-templates.md`, заготовка `line-task.md` + оговорка о родословной. + +Вторая половина того же решения (узкую перепроверку после триажа отдавать +линзе, видящей дифф триажа целиком) сработала: перепроверка ушла той же +линии TASK, и ей отдельно задан вопрос про `tests/dag-probes-unit.py` — +файл, которого в тикете не было и который исполнитель добавил на починке. + +Две сильнейшие находки линии TASK в этом прогоне — из класса, который +новая формулировка называет прямо, а старая не называла: молчаливый опрос +`1800 × docker compose exec` (выглядит как 90 с, на деле ~8 мин при 0,36 с +на итерацию) — несоразмерность; пробник, не проверявший, на каком шарде +оказался его маркер, — проверка без доказательства своего утверждения. + +Правки того же дня прошли слепое ревью по `/writing-great-skills` +(CHANGES_REQUIRED, 5 MAJOR): пять примеров в линзе сокращены до трёх с +ведущим словом `Taste:`, разрез по родословной переведён с цитаты фразы на +блок целиком, снята устаревшая копия описания линзы в SKILL.md. Ревью +подтвердило, что само расширение линзы не пустышка: прежний текст был +целиком про соответствие постановке, и вкусовая находка уезжала бы в +«вне скоупа». + +## 2026-07-31: казусы координации (прогон #18, тот же день) + +- Молчание субагента ≠ смерть. Клод-ревьюер шёл 59 минут, не сбрасывая + транскрипт на диск (153 байта с момента старта). Оркестратор счёл его + мёртвым и поднял дубль — тот писал бы вердикт в ТОТ ЖЕ путь и затёр бы + находки; спасло только то, что уведомление пришло раньше. Правила: + признак жизни — уведомление харнесса, не размер журнала; замене давай + ДРУГОЙ путь вердикта; в обёртке проси писать индекс инкрементально. +- Отчёт ревьюера о состоянии среды — не факт. Линия CODE вернула «все + долгоживущие службы здоровы», а `kafka` и `prometheus` лежали `exited`: + их погасил её же страж и не поднял. `docker compose ps` без `-a` + погашенных не показывает вовсе — легко принять за здоровый стенд. + Разбор журнала сессии: ревьюер написал `trap ... EXIT` с `make up` и + счёл восстановление состоявшимся, не проверив его. Ровно тот дефект, + который вкусовая линза и должна ловить, — проверка, проходящая без + доказательства собственного утверждения, — только допустил его сам + ревьюер. Заодно оттуда же: он дважды вызвал `spawn_agent`, то есть + развернул своих субагентов вопреки правилу «глубина один». Правило + живёт в SKILL.md для оркестратора и до Codex-ревьюера не доезжает — + писать его в мандат. +- Две линии ревью на одном живом стенде мешают друг другу: стражи гасят + службы и роняют таблицы, параллельная линия получает загрязнённые + прогоны (заметили обе, независимо). Либо стенд одной линии, либо явный + запрет ломающих команд второй. + +- Зелёное из терминала виснет в фоне. Приёмочный прогон встал навсегда на + `make smoke-cluster`: `clickhouse-client` у запроса INSERT дочитывает + данные со стандартного ввода и ждёт его конца, а у фонового процесса + конец не наступает. Из терминала та же команда всегда была зелёной, ни + одно из двух ревью этого не видело. Приёмка оркестратора нашла то, чего + не нашли обе линии — потому что запускала иначе. + +Поглощено рефакторингом 2026-07-31: обёртка Клод-ревьюера +(инкрементальная запись индекса), «Сбои координации» SKILL.md (признак +жизни — уведомление; замене — другой путь вердикта; среда — своими +глазами), этап 4 (стенд одной линии), этап 6 (stdin фонового запуска), +мандат review-boilerplate (глубина один; проверка восстановления среды). + +**Цифры:** тикет — 20 критериев, переписан дважды (двойное ревью постановки +сняло невозможный критерий: ноды кластера — шарды, не реплики). Саморевью +исполнителя 3/2. Слепые ревью: CODE — APPROVED без находок, TASK — 8; +перепроверка мутациями добавила ещё 2, все 10 закрыты. Приёмка на чистых +томах: `make up` 116 с, `make smoke` 25/0, память стенда 2244,0 MiB при +пороге 3,4 ГБ, `make smoke-cluster` 8/8 за 7 с — и одно зависание на 23 +минуты до починки. + +### Открытый вопрос 2026-07-31 — закрыт рефакторингом того же дня + +- Константы — файлами в `prompts/`: line-task, line-code, line-rev, + self-review; вкусовая линза с базой двенадцати запахов Фаулера из + `/code-review` Мэтта Покока — `line-taste.md`, разрез — выбором файла + в `cat`. Оттуда же правило «линии не сливать в один ранжир» — этап 5. +- Третья ось — вкус: матрица Тео (@t3dotgg) получена от пользователя с + поправкой под gpt-5.6-sol/Opus 5 (интеллект вырос, вкус прежний) — + references/model-matrix.md. Разрез по подзадачам на этапе 1, сначала + вкусовая часть (задаёт форму), один писатель в дереве — в силе. +- «Родословная» разведена на **семейство** (классы находок) и + **свежесть** (независимость от автора): «Роли» и этап 4 — линия + дефектов по различию семейства, линия уместности по умению (модель со + вкусом), при высокой цене ошибки уместность — третьей модели. Перенос + из `AGENTS.md` стенда кликстрима состоялся. +- Дополнение того же дня (решение пользователя): вкусовую реализацию + ведёт `craftsman` (opus, `medium`) — ошибка реализации громкая, + конвейер ловит, вкус едет с моделью, не с эффортом; `high` на + реализации не дефолтить. +- Слепое ревью рефакторинга (Опус, по writing-great-skills): + CHANGES_REQUIRED — 7 MAJOR, 17 MINOR, 3 NIT; закрыто тем же днём. + Главное: эффорт-карта с обоснованиями демотирована в claude-agents.md + (SSOT — там, где живут `effort:`), хвост «Ролей» ужат втрое, фрагмент + CLAUDE.md приведён к прямому exec и ревью-линии Codex, критерий + этапа 3 обобщён на двух исполнителей, конфликт имён этапа 2 снят + (ревьюер постановок — `deep-reasoner`). Отклонено два: порог + «вкус ≥ 7» (содержательная граница: пропускает Sonnet, отсекает Sol) и + мандат внутри определения `craftsman` (определение уезжает в + репозитории без скилла — самодостаточность важнее дедупликации). +- Позже тем же днём (решение пользователя): три Опус-определения + избыточны — определений нужно ровно столько, сколько различных пар + (модель, ступень) в карте, а роли живут в бриф-файлах. + `adversarial-reviewer` слит в `craftsman` (opus, medium — исполнение + брифов: вкусовая реализация, слепое ревью, перепроверки); упоминание + заготовки adversarial-reviewer в записях выше — история того дня. + diff --git a/agents/.agents/skills/claude-subagent-playbook/references/lessons.md b/agents/.agents/skills/claude-subagent-playbook/references/lessons.md index f18c008..933e268 100644 --- a/agents/.agents/skills/claude-subagent-playbook/references/lessons.md +++ b/agents/.agents/skills/claude-subagent-playbook/references/lessons.md @@ -1,547 +1,18 @@ # Эмпирика прогонов Датированные факты: что поймал каждый этап конвейера, казусы, цифры. -Дописывай после каждого прогона — это и есть «выжимка опыта», ради которой -скилл существует. Журнал накопительный, поэтому дистиллируй: когда урок -поглощён SKILL.md или references, сжимай его запись здесь до строки-факта -(дата, что случилось, куда поглощено) — иначе файл растёт бесконечно. -Новые факты прогона дописывай свободно; дистилляцию и правку старых -записей согласуй с пользователем — это долговечная эмпирика. - -## 2026-07-06 — t2-ml-forecast, задача 05 (первый прогон; дистиллировано 2026-07-12) - -- Свежий взгляд на постановку окупился: блокер name_ru (в данных — английский), - две «одностроки» с проектными решениями, дыра регенерации `.ipynb`. - Поглощено: SKILL.md этап 2. -- Казус форвардера: субагент, получив постановку вместо команды, реализовал - задачу сам (+1227 строк). Поглощено: SKILL.md этап 3, codex-exec (раннер). -- Слепое двойное ревью: пересечение находок — ноль; Клод подтвердил математику - и артефакты, Codex нашёл две дыры в тестах. Поглощено: SKILL.md (роли). -- Смерть фонового ревьюера без доставленного отчёта; транскрипт не спас. - Поглощено: SKILL.md этап 4 (вердикт — файлом, сообщение — указателем). -- Цифры: ревью постановки ~60k токенов; конвейер ~3 часа, реализация ~20 мин. - -## 2026-07-07 — наглядность витрины (полный конвейер; дистиллировано 2026-07-12) - -- Idle-уведомление ≠ отчёт; голый поллер вне run_in_background умирает при - смене хода; статус job — не истина (зомби «running» после смерти воркера: - истина — mtime артефакта + лог + pgrep). Поглощено: SKILL.md - («Пользователь в петле»), codex-exec (фоновый запуск, раннер). -- Безадресный resume подхватывает чужой тред. Поглощено: codex-exec. -- Доводы отклонений — в файл задачи (свежий тред продолжает без контекста - предшественника). Отменено 2026-07-19: доводы — в файл отчёта триажа, - свежий тред получает его путём; тикет в триаже не правится (эхо файла - задачи, прогон 13). Поглощено: prompts/triage-header.md, SKILL.md 5–6. -- Не поглощено (держать в уме при постановке): правила задачи ранжировать - явно («правило A главнее буквы E») — внутренние противоречия всплывают - после починки. -- Цифры: реализация 18 мин; триаж ~8 мин; тесты 147 -> 154. - -## 2026-07-09 — local-transcriber, SendTo (первый под Windows; дистиллировано 2026-07-12) - -- Git Bash-стек работает целиком; классификатор режет companion `--write`, - прямой `codex exec` проходит. Поглощено: codex-exec. -- Свежий взгляд: 2 major (OEM-кодировка `.cmd` на кириллическом профиле, - протухание пути venv) + load-bearing порядок проверок. Поглощено: этап 2. -- Отписка: вердикт одной строкой, проверка по JSONL подтвердила работу. - Поглощено: SKILL.md этап 4, codex-exec. -- Эмпирический ревьюер (воспроизведение краевых случаев вне репо) — вердикт - твёрже. Поглощено: SKILL.md этап 4, boilerplate шаблонов. -- Цифры: ревью постановки ~57k, кода ~48k, перепроверка ~45k токенов. - -## 2026-07-10 — четыре записи (дистиллировано 2026-07-12) - -- Ревьюер Codex без read-only: мандат промптом надёжен, песочница не режется. - Поглощено: codex-exec (ветка ревьюера). -- Sandbox-инцидент CLI 0.144.1 (bwrap+userns vs AppArmor) и ловушка memfd - (профиль на путь bwrap не цепляется — вешать на бинарь codex). Поглощено: - codex-exec + codex-sandbox-apparmor.md. -- Постановка через `/to-tickets` ложится в конвейер без трения; двойное - слепое ревью постановки окупилось (Клод — механика кода, Codex — уровень - требований; пересечение 2 из ~15). Поглощено: SKILL.md этапы 1–2. -- Ретро расхода контекста (3 цикла): находки проходили через оркестратора - до шести раз; review-промпт дублировался; ~7 пустых ходов на idle-пингах. - Поглощено: SKILL.md (роль оркестратора: индекс, cat, файлы), шаблоны. - -## Прогон 2026-07-12: clickstream-demo, задача 20 — флаки runtime-гейта - -Полный конвейер + три захода стендовой приёмки. Главный урок прогона: -**ревью по чтению кода не заменяет сквозный прогон** — два класса дефектов -вскрылись только на стенде. - -**Что поймал каждый этап:** -- Ревью постановки (Opus): настоящий корень — отсутствие SIGTERM-хендлера - (python PID 1, SIGKILL после grace); один из двух вариантов фикса в - постановке гонку не закрывал. Плюс критерий «красный сценарий всё ещё - ловится» и запрет вероятностных смягчений. -- Слепые ревью: Codex — grace-период 10с и обходимость precheck (пара из - старой backfill-строки); Клод — подтвердил структурный довод, на узкой - перепроверке принёс НОВУЮ находку (тест биндил порт 9109 — флаки 1/13). - Пересечение — 2 темы из ~8 (grace, слабый контракт-тест): не «стабильно - ноль», но малое; обе родословные оправдались. -- Стендовая приёмка (3 захода): (1) гейт годами жил на побочном эффекте - бага — пересекающие визиты давала «нелегальная переработка» генератора - после игнорируемого SIGTERM; честный фикс оставил проверку без сырья; - (2) таймзона: наивные метки STG (UTC) против границы с `+00:00` на - сервере Europe/Moscow — precheck был зелёным вакуумно; та же ошибка — в - приёмочном скрипте координатора (наивная конвенция DDS). Урок: сравнение - времени в SQL — только с явным поясом с обеих сторон. - -**Ретро контекста оркестратора** (главный пожиратель — внеплановые циклы): -диагнозы падений приёмки велись мастером инлайн (~15 вызовов); boilerplate -промптов переписывался трижды; обменные файлы шли кириллицей (×1,5–2); -правки задачи-файла — тремя крупными Edit (old+new = двойной текст); -промпты будильников пересказывали план. Поглощено 2026-07-12: SKILL.md -(принцип «мастер решает — субагенты выясняют», стоп-кран «сам — максимум -один заход», механика — fast-worker'у, обменные файлы на английском, -будильник одной строкой, сквозная проверка до ревью, фолбэк ревьюера -deep-reasoner — обкатан этим прогоном), prompt-templates + prompts/ -(готовые boilerplate-файлы, английские скелеты), codex-exec (модель -gpt-5.6-sol, medium для узких починок, ловушка `&`). Слепое Fable-ревью -самого скилла (по глоссарию writing-great-skills): восстановление после -rm -rf подтверждено без потерь, 9 MINOR + 5 NIT согласованности — все -закрыты тем же днём. - -**Прочее:** казус двойного фона (`&` при run_in_background) — спасён -ожидателем `kill -0`; принятие остаточного риска (публикация не ограничена -по времени) зафиксировано доводом в задаче — паттерн «риск принят + после -фикса такой отказ падает громко и честно» работает как аргумент приёмки. -Отдельный казус координатора: `rm -rf` «зеркала» скилла прошёл сквозь -симлинк `~/.claude/skills -> dotfiles` и снёс оригинал; восстановлено из -git (`git show HEAD:path`) + повторным наложением правок из контекста. -Урок: перед rm — `ls -la` цели и родителя, симлинк-родитель = чужая -территория. - -**Цифры:** реализация ~25 мин; ревью постановки 75k токенов субагента, -ревью кода 65k, перепроверка 80k (с новой находкой); приёмка — 4 прогона -гейта по ~1,5 мин + красный сценарий; тесты 190 -> 192 + 21. - -## Прогон 2026-07-12/13: clickstream-demo, задача 13 — глагол next-day - -Первый прогон после поглощения уроков задачи 20 — они сработали: вердикты -читались по одному разу, boilerplate не переписывался (cat из prompts/), -обмен на английском, ноль инлайн-диагнозов мастера (стоп-кран держит), -будильники одной строкой (9 взводов, ни один не сработал впустую — все -сняты по уведомлениям). - -**Что поймал каждый этап:** -- Двойное ревью постановки: пересечение 5 тем из ~15 (guard, идемпотентность, - атомарность, формат цепочки, проверки). Уникальное: Клод — «next-day = - новый режим запуска, постановка прячет основную работу за словом - „переиспользует"»; Codex — «расписание запустит дефолтный backfill» - (скоуп-решение: расписание вынесено отдельной задачей). -- Слепые ревью кода: пересечение 1 тема из ~12 (нулевой стык). Codex — - дефекты нового скрипта (хвост за границей, TZ), Клод — архитектура - (retention Kafka против пересборки счётчиков — блокер будущей задачи, - скрытая связка наборов настроек). Родословные разошлись почти полностью. -- Эмпирика исполнителя: требование обоих ревью («громкий отказ на нулевом - стыке») покраснело на честном стенде — ночной провал трафика, снова класс - «артефакт верификатора». Диагноз по данным делегирован исполнителю тем же - тредом (state на границе: 0 активных визитов — restore ни при чём). - Урок: требование ревьюеров сверяй с критериями приёмки и реальным - распределением данных, прежде чем принять его в код. -- Узкая перепроверка Codex снова принесла новый MAJOR (микросекунды в - UTC-нормализации) — второй прогон подряд, считать штатным режимом. - -**Новые пожиратели контекста мастера, по убыванию:** -1. Эхо файла задачи: исполнитель дописал резолюции в тикет, который мастер - сам писал на этапе 2, — харнесс вкатил в контекст все ~190 строк; итого - текст тикета прошёл через мастера трижды (Write + эхо + финальное - чтение). Не поглощено; митигация неочевидна — резолюции проекту нужны - именно в тикете. Держать в уме при выборе, кто пишет файл задачи. -2. Клод-ревьюер держит формат индекса хуже Codex: многострочные находки и - развёрнутые confirmations при жёстком boilerplate («one-phrase essence»). - Поглощено: обёртка Клод-ревьюера в prompt-templates дополнена - напоминанием об однострочности. -3. Авторство решений этапа 2 — у мастера по определению (110 строк - кириллицы в тикет после двойного ревью постановки): это цена этапа, на - мелких задачах конвейер не разворачивать (правило уже в SKILL.md, - теперь с ценником). - -Дешёвый приём: вердикт перепроверки Клода взят из строки task-notification -(обёртка требует финальным актом только VERDICT-строку) — файл не читался. - -**Цифры:** конвейер ~2 часа от ревью постановки до приёмки; реализация -~30 мин; Клод-субагенты: ревью постановки 94k, кода 108k, перепроверка -126k токенов; Codex-ревью: 42/36 команд; 2 круга триажа + узкий диагноз; -тесты 192 -> 204 + 21 -> 31; учебный цикл: DM 322 -> 10 026 -> 19 196 за -два next-day. - -## Прогон 2026-07-13: t2-presale, тикет 06 — совместимость со средой стенда - -**Главный урок — информирование пользователя.** Статусы на границах этапов -были телеграфными и в терминах плейбука («этап 4», «триаж», «узкая -перепроверка»); эпизодически заглядывающий пользователь потерял нить: -спросил «мы остановились?» при живом фоне, а после финала считал, что -конвейер ещё на ревью постановки и «решение удалили». Фидбек дословно: -«информирование о ходе процесса было очень скудным». Урок: на каждой -границе — карта прогресса 4–7 строк (✅ сделано / ▶ идёт / ⬜ дальше) -обычными словами, термины плейбука только с расшифровкой; карта дополняет -содержательную сводку, не заменяет. Поглощено 2026-07-23: SKILL.md -(«Пользователь в петле») и близнец codex-subagent-playbook -(«Партнёр в петле»). - -**Что поймал каждый этап:** -- Ревью постановки с эмпирикой перекроило тикет до реализации: Codex из - контейнера установил, что во внутренних зеркалах duckdb нет вовсе - (BLOCKER → план Б wheel'ом с публичного PyPI) и что названный в тикете - кандидат convert_dtypes теряет точность через float64 — исполнитель - сразу пошёл верным путём. -- Фактическое противоречие ревьюеров (верхний cp37-wheel duckdb: «0.10.3» - у Клода против «1.2.2» у Codex) оркестратор снял ОДНОЙ контрольной - командой (`pip download` в контейнере) до триажа — дёшево, а от факта - зависел пин. Приём: конфликт фактов — контрольный эксперимент, не - голосование. -- Слепые ревью кода: пересечение БОЛЬШОЕ (одна корневая тема — регрессии - нового вывода типов против старого пути: int64-переполнение роняло - загрузку, пробелы, BOOLEAN, inf). Контрпример к «пересечение ~ноль»: - когда правка замещает хорошо определённое старое поведение, обе - родословные сходятся на охоте за регрессиями — и это признак качества - находок, а не растраты. -- Перепроверка снова принесла хвост (смесь конечных с inf/-inf — DOUBLE): - третий прогон подряд, подтверждён штатный режим. - -**Прочее:** сетевые шаги с доступами пользователя (docker login/pull) -координировались `!`-командой в чат — работает без трения. Первый полный -прогон на gpt-5.6-sol как боевой модели — пользователь подтвердил цену, -качество исполнителя и ревьюера без нареканий. - -**Цифры:** постановка + двойное ревью постановки ~1 ч; реализация ~25 мин; -2 круга триажа + 2 узкие перепроверки; тесты 36 → 45 → 46, зелёные в двух -средах (современная + vendor-контейнер py3.7); приёмка оркестратора — оба -прогона своими руками. - -**Модели (датированная эволюция, к прогону 2026-07-13):** -- Урок о скоропортящихся фактах: 2026-07-10 утечка gpt-5.6-sol из конфига - считалась казусом («фронтир = дорогие лимиты»), 2026-07-13 пользователь - переоценил — Sol умная и относительно недорогая, теперь боевой дефолт. - Правило «модель явно, из конфига не наследовать» выжило, но по другой - причине: воспроизводимость, а не цена. Факты о ценах/лимитах моделей — - датировать и перепроверять у пользователя, не тащить из прошлых сессий - как вечную истину. -- Effort medium на узких контурах подтверждён боем: круг починки одной - находки и финальная перепроверка — чисто и быстрее high (до этого - правило в codex-exec было гипотезой). -- Роли от пользователя (2026-07-13): Опус — вкус и архитектура; Codex — - исполнитель (лучше и дешевле); исследование — паритет, Codex дешевле. - Кандидат на поглощение в SKILL.md (раздел «Роли»). -- НЕ ОБКАТАНО (рыночная наводка из обзоров, 2026-07-13): gpt-5.6-terra - medium/high для кода — на medium вдвое дешевле Sol на простых задачах - при том же уровне, сильно лучше Sonnet; минусы — ощутимо дольше запуск и - накладные на внешнюю оркестрацию. Вывод на сейчас: лимиты Codex у - пользователя не узкое место, менять нечего; потенциальная полоса — - bulk-механика /coordinator-loop и узкие починки, если лимиты станут - узкими. Проверка — один A/B на реальной узкой починке. - -## Прогоны 2026-07-20/21: headless-xray-proxy, задачи 03–04 — эксперимент «реализация на medium» - -- Дизайн: реализация Codex на `medium` (03 — жизненный цикл процессов, - 04 — проверяемая установка), остальное по правилам 2026-07-19; baseline — - задача 06 на high (1 MAJOR + 1 NIT от слепых ревью). -- Качество: 03 → 4 MAJOR (все — гонки конкурентности/восстановления), - 04 → 2 MAJOR, из них один (CODE-1) — дефект ПОСТАНОВКИ, не исполнителя. - Конвейер всё выловил и починил; «чистых» MAJOR реализации в 04 — один, - на уровне baseline. -- Экономика: 03 дешевле baseline (~636k+77k против ~735k+97k свежих - Codex-токенов), 04 — ДОРОЖЕ (~822k+135k): экономию реализации съел - триаж семи находок. Урок: экономию эффорта считать по конвейеру целиком. -- Казус CODE-1: spec-review на high уверенно выдумал несуществующий - однострочный формат `SHA256=` в `.dgst` (реальный — четыре записи - `MD5=`/`SHA1=`/`SHA2-256=`/`SHA2-512=`); дефект уехал в тикет и код, - пойман только слепым CODE-ревью, стоил поправки тикета до триажа. - Урок: внешние факты (форматы артефактов, версии релизов) эффортом не - лечатся — проверять реальным скачиванием/фикстурой из первоисточника. -- Эмпирика кэша Codex: смена `model_reasoning_effort` high→medium при - `resume` кэш треда не сбрасывает (~93–94% кэша во всех трёх задачах). -- Казусы харнеса: рестарт сессии дважды убивал фоновый codex — тред - спасался по сохранённому thread_id; `codex exec resume` принимает - ТОЛЬКО `-c`-оверрайды (`-s`/`-m`/`-o` → exit 2); usage убитого хода - теряется (нет `turn.completed`) — фиксировать с оговоркой из resume-хода. -- Решения пользователя 2026-07-21 (поглощено: codex-exec.md — эффорт, - SKILL.md — эффорт-карта Claude-субагентов): реализация по - отревьюированному тикету → medium допустим; Claude-субагентам effort - задавать явно — xhigh постановки/планы, high слепое ревью, medium - перепроверки; ревью ниже high не опускать. **Пересмотрено 2026-07-26** - (см. ниже) — карта сдвинута на ступень вниз под Opus 5. - -## Прогон 2026-07-21: yantar-dags, предразметка — этап постановки - -- Issues в GitLab созданы по конвенции репозитория, но мимо критериев - `/to-tickets`: без критериев приёмки чекбоксами, один тикет — два среза - (две разные точки стендовой проверки). Поймал пользователь сверкой ПОСЛЕ - публикации. Урок: сверка разбиения — до публикации, внутри `/to-tickets`. -- Пользователь заметил избыточность: текст тикета проходил через мастера - трижды (создание + проверка после создания + тщательное ревью перед - выполнением) — по времени и токенам. Поглощено 2026-07-21: SKILL.md - этапы 1–2 — `/to-tickets` как норма разбиения с меркой «тикет берётся в - свежей сессии без общего контекста»; правило «одно ревью на версию - артефакта» (сверка с пользователем = первая линия); шкала риска этапа 2 - (срез по принятой спеке без новых решений — внешнюю линию пропустить с - одной фразой обоснования). - -## Прогон 2026-07-22: clickstream-demo, issue #5 — счётчики стартовой истории - -Полный конвейер (исполнитель → два слепых ревью → триаж → узкая -перепроверка → стендовая приёмка) дошёл до цели, но шёл под ЧУЖИМ скиллом: -вместо этого плейбука вызван codex-subagent-playbook — близнец для -координатора на стороне Codex, на тот момент единственный из пары видимый -модели для автовызова. Отсюда главный казус: канал запуска Codex -«унаследовался» из handoff — конвейер пошёл через плагин-обёртку вопреки -codex-exec.md и воспроизвёл её известные баги (ложный «started» с подменой -ответа — issue #158, потерянные уведомления, несбрасываемый статус -остановленной задачи, read-only песочница ревьюера — вердикт извлекали из -лога задачи). Спас файловый контроль: мандаты и отчёты жили в `$SCRATCH`, -дерево сверялось тестами. Поглощено 2026-07-23: близнецу поставлен -`disable-model-invocation` и адресное описание («со стороны Claude Code — -claude-subagent-playbook»); правила канала в codex-exec.md были и остаются -действующим договором. - -Казус двух исполнителей: молчащего исполнителя заменили свежим без -остановки прежнего — в одном дереве оказались два писателя, дерево -пришлось перепроверять тестами. Поглощено: «Сбои координации» (владение — -только после остановки прежнего владельца). - -Казус приёмки: сценарий стендовой приёмки трижды падал на непроверенных -командах (способ аутентификации Airflow, маскировка кода выхода, имя -колонки витрины), а инлайн-python с экранированием в heredoc сломался и -после проверки. Поглощено: SKILL.md этап 6 (команды нового сценария — на -живом объекте до полного прогона, сложные вставки — файлами). Попутно: -`pkill -f` в одной команде с запуском/ожиданием находит шаблон в -собственной командной строке и убивает свой же Bash — дисциплина фоновых -процессов зафиксирована в памяти проекта. - -**Цифры:** триаж закрыл обе находки ревью (фрагментация наборов ID сняла -потолок Kafka: манифест 3 152 байта вместо ~0,81 МБ); приёмка — плоское -время next-day 716/718/716 с, мир 3 → 6 дней, 561 942 события; тесты -216 + 31 зелёные. - -## 2026-07-23: сверка близнецов после промаха скиллом - -В кодексовый близнец перенесены проверенные здешними прогонами правила: -одно ревью на версию артефакта, саморевью исполнителя и сквозная проверка -до внешних линий, цена тихой ошибки как критерий уровня, проверка внешних -фактов первоисточником, партнёр в петле. Обратно взяты «Пределы -параллельности» (глубина один; второй обзор ради отдельной линии, а не -свободного слота) — в SKILL.md, раздел «Роли». Скилл переведён на -автовызов моделью (описание с триггерами), близнец скрыт -`disable-model-invocation` — пара промахов исключена с обеих сторон. - -## 2026-07-23: taste-слепота триажа — «закрыть находку тестом» - -Прогон course-labs-redesign (issue #7, docs-only). Codex на триаже закрыл -9 из 10 находок честно, но каждую сопроводил контрактным тестом с -дословной цитатой учебной прозы (+7 хрупких тестов в -test_world_dags_contract.py: «не сравнивай», «днём 5» и т.п.). Формально -безупречно — «regression-тест на находку», по сути мусор: прибитая фраза -падает при любом честном рерайте текста, а не при дефекте. Обе линии -слепого ревью прошли раньше триажа и этого видеть не могли; поймал -пользователь, читая незакоммиченный дифф. - -Решения пользователя (перенесены в память проекта: -claude-reviews-code-meaningfulness): 1) в линзу Claude-ревьюера добавлять -осмысленность кода — «заслуживает ли существования каждый добавленный -артефакт», не только соответствие постановке; 2) срезание/переписывание -бессмысленного кода поручать Опусу, не Codex («у него куда лучше вкус»). -Механика: узкую перепроверку после триажа давать той линзе, что видит -дифф триажа целиком, — иначе taste-дефекты триажа не увидит никто. - -Попутно: образец заражает — исполнитель добавлял прозаические тесты, -следуя уже существующим в файле (жанр «тест на фразу README» там был до -него). Чистка легаси-жанра — отдельным issue (#24), не в ветке фичи. - -## Решение пользователя 2026-07-26: эффорт-карта Claude-субагентов под Opus 5 - -Скилл писался под Opus 4.8; у Opus 5 усилия распределены иначе, и `high` -стал верхней рабочей ступенью — выше неё смысл появляется редко. Карта в -SKILL.md сдвинута на ступень вниз: `high` — ревью постановок и планов -(было `xhigh`); `medium` — слепое ревью (было `high`) и узкие -перепроверки; default — механика. Нижняя граница ревью опущена с `high` -до `medium`. - -Сдвиг неравномерный (оценка пользователя, заведомо условная): `high` у -Opus 5 по отдаче ближе к прежнему `xhigh`, а `medium` — чуть ниже -прежнего `high`. То есть на ревью постановок потеря близка к нулю, а на -слепом ревью просадка есть, но меньше, чем выглядит по названию ступени. - -Следствие: ступеней теперь меньше, чем этапов, — слепое ревью и узкие -перепроверки делят `medium`. Это осознанно: эффорт задаёт лишь потолок -глубины поверх выбранной модели, тонкая настройка идёт промптом. - -`deep-reasoner` остаётся на `high` (решение пользователя): понижать -специалиста по рассуждению не надо. В роли фолбэк-ревьюера он приедет -ступенью выше карты — принято осознанно, карта задаёт минимум для роли, -а не потолок для агента. - -Оси не путать: механика едет на Sonnet (`fast-worker`, модель пришита в -определении), и ярус «default» там означает «эффорт не крутить», а не -дешёвый режим Опуса. - -Не изменилось: эффорт Codex (`references/codex-exec.md`) — там своя -шкала, по сложности; запрет менять effort между резюмами одного треда; и -главный предел — от уверенной выдумки внешних фактов не страхует никакой -эффорт (казус CODE-1). - -### Открытый вопрос 2026-07-26 — закрыт 2026-07-31 - -Проверено по схеме Agent-тула: ручки `effort` у него нет — ступень -задаётся только `effort:` во фронтматтере определения агента или -`opts.effort` в Workflow. Поглощено рефакторингом 2026-07-31: карта в -SKILL.md переписана на определения, в claude-agents.md добавлена -заготовка `adversarial-reviewer` (opus, medium), фолбэк «скептический -general-purpose» снят. - -### 2026-07-30: классификатор авторежима блокирует `-s danger-full-access` - -На запуске Codex-исполнителя (прогон тикета #12, кластер ClickHouse) -классификатор авторежима Claude Code заблокировал команду с -`-s danger-full-access`. Рабочая замена — не полный доступ, а песочница -с поштучной эскалацией: - -``` --s workspace-write \ - -c 'approval_policy="on-request"' \ - -c 'approvals_reviewer="auto_review"' -``` - -Команда, которую песочница не пустила (docker и т.п.), эскалируется, и -авто-ревьюер Codex её одобряет — запуск уходит мимо песочницы штатно. - -Почему это лучше, а не просто обход: привилегия меньше («всё разрешено -заранее» → «поштучно и в логе»), и на приёмке можно посмотреть, какие -именно команды прошли мимо песочницы, — с полным доступом такого списка -не существует. Оговорка: `auto_review` делает песочницу совещательной — -эскалации одобряет автоматика самого Codex, поэтому мандат «исходники -вне ветки не трогать, окружение не ломать» по-прежнему держится на -промпте, не на песочнице (см. правило в SKILL.md). - -Классификатор при этом не враг: по отзывам сообщества, именно он в -авторежиме иногда спасает данные от разрушительных команд. Считать его -подсказкой «сузь привилегию», а не препятствием, которое надо обойти. - -Дополнение по итогам прогона (тот же день): рецепт исполнителя в -`codex-exec.md` штатную связку уже содержал — `danger-full-access` был -отступлением сессии-оркестратора «на всякий случай» под docker. Прогон -подтвердил, что запас не нужен: под штатной связкой у Codex прошли и -сеть (`docker manifest inspect`), и docker-сокет (`make up`, `docker -compose down`); отдельных событий эскалации в `--json`-логе нет — -успешные команды выглядят обычными `completed`. Кавеаты в -`codex-exec.md` обновлены, пометка «боем не обкатано» снята. - -## 2026-07-31: решение о вкусовой линзе неделю не доезжало до механизма - -Прогон clickstream-data-platform, тикет #18 (пробные DAG в Airflow). -Решение 2026-07-23 («в линзу Клод-ревьюера — осмысленность кода») жило в -записи уроков и в памяти ТОГО проекта, но в `prompts/`/`prompt-templates.md` -не попало. Оркестратор собрал линию TASK `cat`'ом из заготовки — и ревьюер -не был обязан спрашивать «не дичь ли это». Пользователь заметил это сам, -по ходу прогона, дословно: «Бывает когда сделано формально правильно, а по -сути - дичь». - -Урок общий: решение, записанное только в уроки, следующим прогоном не -исполняется. Память пообъектная — в другой репозиторий она не едет; ехать -может лишь механизм, который подшивается в промпт. Поглощено 2026-07-31: -`prompt-templates.md`, заготовка `line-task.md` + оговорка о родословной. - -Вторая половина того же решения (узкую перепроверку после триажа отдавать -линзе, видящей дифф триажа целиком) сработала: перепроверка ушла той же -линии TASK, и ей отдельно задан вопрос про `tests/dag-probes-unit.py` — -файл, которого в тикете не было и который исполнитель добавил на починке. - -Две сильнейшие находки линии TASK в этом прогоне — из класса, который -новая формулировка называет прямо, а старая не называла: молчаливый опрос -`1800 × docker compose exec` (выглядит как 90 с, на деле ~8 мин при 0,36 с -на итерацию) — несоразмерность; пробник, не проверявший, на каком шарде -оказался его маркер, — проверка без доказательства своего утверждения. - -Правки того же дня прошли слепое ревью по `/writing-great-skills` -(CHANGES_REQUIRED, 5 MAJOR): пять примеров в линзе сокращены до трёх с -ведущим словом `Taste:`, разрез по родословной переведён с цитаты фразы на -блок целиком, снята устаревшая копия описания линзы в SKILL.md. Ревью -подтвердило, что само расширение линзы не пустышка: прежний текст был -целиком про соответствие постановке, и вкусовая находка уезжала бы в -«вне скоупа». - -## 2026-07-31: казусы координации (прогон #18, тот же день) - -- Молчание субагента ≠ смерть. Клод-ревьюер шёл 59 минут, не сбрасывая - транскрипт на диск (153 байта с момента старта). Оркестратор счёл его - мёртвым и поднял дубль — тот писал бы вердикт в ТОТ ЖЕ путь и затёр бы - находки; спасло только то, что уведомление пришло раньше. Правила: - признак жизни — уведомление харнесса, не размер журнала; замене давай - ДРУГОЙ путь вердикта; в обёртке проси писать индекс инкрементально. -- Отчёт ревьюера о состоянии среды — не факт. Линия CODE вернула «все - долгоживущие службы здоровы», а `kafka` и `prometheus` лежали `exited`: - их погасил её же страж и не поднял. `docker compose ps` без `-a` - погашенных не показывает вовсе — легко принять за здоровый стенд. - Разбор журнала сессии: ревьюер написал `trap ... EXIT` с `make up` и - счёл восстановление состоявшимся, не проверив его. Ровно тот дефект, - который вкусовая линза и должна ловить, — проверка, проходящая без - доказательства собственного утверждения, — только допустил его сам - ревьюер. Заодно оттуда же: он дважды вызвал `spawn_agent`, то есть - развернул своих субагентов вопреки правилу «глубина один». Правило - живёт в SKILL.md для оркестратора и до Codex-ревьюера не доезжает — - писать его в мандат. -- Две линии ревью на одном живом стенде мешают друг другу: стражи гасят - службы и роняют таблицы, параллельная линия получает загрязнённые - прогоны (заметили обе, независимо). Либо стенд одной линии, либо явный - запрет ломающих команд второй. - -- Зелёное из терминала виснет в фоне. Приёмочный прогон встал навсегда на - `make smoke-cluster`: `clickhouse-client` у запроса INSERT дочитывает - данные со стандартного ввода и ждёт его конца, а у фонового процесса - конец не наступает. Из терминала та же команда всегда была зелёной, ни - одно из двух ревью этого не видело. Приёмка оркестратора нашла то, чего - не нашли обе линии — потому что запускала иначе. - -Поглощено рефакторингом 2026-07-31: обёртка Клод-ревьюера -(инкрементальная запись индекса), «Сбои координации» SKILL.md (признак -жизни — уведомление; замене — другой путь вердикта; среда — своими -глазами), этап 4 (стенд одной линии), этап 6 (stdin фонового запуска), -мандат review-boilerplate (глубина один; проверка восстановления среды). - -**Цифры:** тикет — 20 критериев, переписан дважды (двойное ревью постановки -сняло невозможный критерий: ноды кластера — шарды, не реплики). Саморевью -исполнителя 3/2. Слепые ревью: CODE — APPROVED без находок, TASK — 8; -перепроверка мутациями добавила ещё 2, все 10 закрыты. Приёмка на чистых -томах: `make up` 116 с, `make smoke` 25/0, память стенда 2244,0 MiB при -пороге 3,4 ГБ, `make smoke-cluster` 8/8 за 7 с — и одно зависание на 23 -минуты до починки. - -### Открытый вопрос 2026-07-31 — закрыт рефакторингом того же дня - -- Константы — файлами в `prompts/`: line-task, line-code, line-rev, - self-review; вкусовая линза с базой двенадцати запахов Фаулера из - `/code-review` Мэтта Покока — `line-taste.md`, разрез — выбором файла - в `cat`. Оттуда же правило «линии не сливать в один ранжир» — этап 5. -- Третья ось — вкус: матрица Тео (@t3dotgg) получена от пользователя с - поправкой под gpt-5.6-sol/Opus 5 (интеллект вырос, вкус прежний) — - references/model-matrix.md. Разрез по подзадачам на этапе 1, сначала - вкусовая часть (задаёт форму), один писатель в дереве — в силе. -- «Родословная» разведена на **семейство** (классы находок) и - **свежесть** (независимость от автора): «Роли» и этап 4 — линия - дефектов по различию семейства, линия уместности по умению (модель со - вкусом), при высокой цене ошибки уместность — третьей модели. Перенос - из `AGENTS.md` стенда кликстрима состоялся. -- Дополнение того же дня (решение пользователя): вкусовую реализацию - ведёт `craftsman` (opus, `medium`) — ошибка реализации громкая, - конвейер ловит, вкус едет с моделью, не с эффортом; `high` на - реализации не дефолтить. -- Слепое ревью рефакторинга (Опус, по writing-great-skills): - CHANGES_REQUIRED — 7 MAJOR, 17 MINOR, 3 NIT; закрыто тем же днём. - Главное: эффорт-карта с обоснованиями демотирована в claude-agents.md - (SSOT — там, где живут `effort:`), хвост «Ролей» ужат втрое, фрагмент - CLAUDE.md приведён к прямому exec и ревью-линии Codex, критерий - этапа 3 обобщён на двух исполнителей, конфликт имён этапа 2 снят - (ревьюер постановок — `deep-reasoner`). Отклонено два: порог - «вкус ≥ 7» (содержательная граница: пропускает Sonnet, отсекает Sol) и - мандат внутри определения `craftsman` (определение уезжает в - репозитории без скилла — самодостаточность важнее дедупликации). -- Позже тем же днём (решение пользователя): три Опус-определения - избыточны — определений нужно ровно столько, сколько различных пар - (модель, ступень) в карте, а роли живут в бриф-файлах. - `adversarial-reviewer` слит в `craftsman` (opus, medium — исполнение - брифов: вкусовая реализация, слепое ревью, перепроверки); упоминание - заготовки adversarial-reviewer в записях выше — история того дня. +Дописывай после каждого прогона в конец файла — это и есть «выжимка +опыта», ради которой скилл существует. Правку старых записей согласуй с +пользователем: это долговечная эмпирика. + +Журнал накопительный, поэтому у него есть архив: записи с 2026-07-06 по +структурный рефакторинг 2026-07-31 включительно лежат в +[lessons-archive.md](lessons-archive.md) — они описывают заметно другую +редакцию скилла. Живые хвосты тех записей перед переездом сведены в +очередь на механизм (запись 2026-08-03). Когда файл разрастётся снова — +подвинь границу и перенеси старое туда же: архив вне пути чтения +прогона, поэтому его длина ничего не стоит, а дистилляция стоила бы +потерянных историй. ## 2026-07-31: одёргивания за день прогонов (Opus 5-координатор, старая редакция)