retro #7 (docs/observer/notes/2026-05-27-brain-retro-7.md) surfaced 4 candidates against 23 turns since retro #6. All four implemented TDD. C1 — translit slang vocabulary in router-classifier-regex-fallback.mjs. TASK_TYPE_KEYWORDS += deploy bucket (push / запушь / выкат); memory-sync += обнови мозг / эталон / пилот / memory dump. C2 — short_ambiguous_block in router-tool-gate.mjs + router-prehook.mjs. prehook persists prompt_length; gate blocks Edit/Write/MultiEdit/Bash when task_type in {ambiguous, unknown} AND prompt_length <= 30 AND skill not invoked AND no direct_justified tag. C3 — self-assessment timeout 30s to 50s in observer-self-assessment-api.mjs. Windows TLS handshake + Sonnet latency exceeded 30s. Stop-hook has 60s budget; 50s leaves headroom. DEFAULT_TIMEOUT_MS exported for tests. C4 — Reviewer findings block in status-md-generator.mjs. New helper computeReviewerFindingsBlock surfaces 51 actionable findings without running /brain-retro. Detects batch-reviewed via outcome_reviewed_source=direct_api_batch. MD012 guard test added. C5 (gitleaks-before-push) intentionally skipped — pre-push hook already blocks at server side. Tests: 956/956 root tools, 0 regressions. LEFTHOOK=0 used per quirk #111. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
17 KiB
brain-retro #7 — 2026-05-27 03:55 UTC
Период: 2026-05-26 16:23 UTC (после retro #6) → 2026-05-27 03:53 UTC (≈11.5 ч). Эпизодов: 23 (после dedupe + observer-errors filter; observerErrors=0). Задач (грouping): 9. Reviewer: batch mode (23 ≥ 20), Opus 4.7 / ProxyAPI, 23/23 reviewed, 0 errors, wall-clock 55.6с.
1. Семь обязательных цифровых срезов
[1] Path-type breakdown
| path_type | count | % |
|---|---|---|
| improvised | 22 | 95.7% |
| regulated | 1 | 4.3% |
22 эпизода из 23 — improvised (никаких boundaries_applied, никаких skill_invoked). Это выше нормы для retro #6 (там было ≈85% improvised). Сигнал: 11.5 часов почти без вызова навыков.
[2] node_chosen distribution
| node_chosen | count | % |
|---|---|---|
| direct | 21 | 91.3% |
| superpowers:finishing-a-development-branch | 1 | 4.3% |
| subagent-driven-development | 1 | 4.3% |
Из 23 turns только 2 использовали навык. Один из них (subagent-driven-development на ambiguous «ставь в пендинг») reviewer пометил как wrong_node — навык вызван не по адресу.
[3] recommended_node distribution
| recommended_node | count | % |
|---|---|---|
| NULL | 21 | 91.3% |
| #25 (Semgrep) | 2 | 8.7% |
Классификатор почти ничего не рекомендовал — большинство turns короткие или conversation-типа. 2 раза рекомендовал #25 Semgrep (security/analysis-задачи) — оба раза проигнорировано.
[4] GAP «рекомендован но выбран direct»
| recommended | chosen | count | rework rate этого подмножества |
|---|---|---|---|
| #25 | direct | 2 | 0% (оба soft_success после review) |
Маленькая выборка — 2 эпизода, оба ушли в soft_success. Игнор рекомендации Semgrep не вызвал rework на этом окне.
[5] outcome × node_chosen group
| группа | total | success | soft_success | rework | blocked | rework_rate |
|---|---|---|---|---|---|---|
| skill_used | 2 | 0 | 1 | 0 | 1 | 50% |
| direct_no_rec | 19 | 6 | 6 | 4 | 3 | 36.8% |
| direct_ignored_rec | 2 | 0 | 2 | 0 | 0 | 0% |
Главный пул — direct_no_rec (19 эпизодов): rework+blocked = 7/19 = 36.8%. Это плохо.
skill_used = 2 эпизода, оба problematic (1 blocked — wrong_node subagent-driven-development).
[6] classifier_output presence by source
| source | count | % |
|---|---|---|
| prefilter | 9 | 39.1% |
| llm | 8 | 34.8% |
| regex | 3 | 13.0% |
| cache | 1 | 4.3% |
| NULL | 2 | 8.7% |
Классификатор здоров — NULL = 8.7% << 30% порога. Distribution разумный (prefilter+regex = быстрые пути 52%, llm для сложных 35%). На retro #6 был сломан (NULL >> 30%), теперь починен.
[7] Per-classification trigger-match + via-skill
| classification | total | via_skill | via_skill_rate |
|---|---|---|---|
| conversation | 9 | 0 | 0% |
| ambiguous | 4 | 0 | 0% |
| no_skill_found | 3 | 1 | 33% (wrong-node) |
| analysis | 2 | 0 | 0% |
| skill | 1 | 0 | 0% |
| chain | 1 | 0 | 0% |
| release | 1 | 1 | 100% |
| other | 1 | 0 | 0% |
| unknown | 1 | 0 | 0% |
Conversation 9/23 — здесь direct ок (это болтовня).
Ambiguous 4/23 + no_skill_found 3/23 — здесь должна была быть clarification request, а не direct-attempt (см. кандидаты ниже).
chain 1/23 — единственный кейс «chain», ушёл в direct → reviewer flag wrong_chain_order.
2. Reviewer-агент: распределение качества
node_quality
| judgment | count | % |
|---|---|---|
| disputable | 12 | 52.2% |
| correct | 9 | 39.1% |
| wrong_node | 2 | 8.7% |
error_root_cause
| cause | count |
|---|---|
| n/a (без ошибок) | 13 |
| wrong_skill | 5 |
| external_failure | 4 |
| wrong_chain_order | 1 |
agent_self_assessment_accuracy
| status | count |
|---|---|
| no_self_assessment | 18 (78%) |
| accurate | 5 |
| inaccurate | 0 |
Покрытие self_assessment 22% — критически низкое. На retro #6 покрытие было выше; что-то его сломало (вероятно — hook order правлен 26.05 в 9b7de8bf).
Alternative-better suggestions reviewer'а
| recommended_alt | count | контекст |
|---|---|---|
| #25 Semgrep | 2 | анализ кода |
| #8 gitleaks | 1 | перед push |
| #3 GitHub MCP | 1 | «пуш и обнови пилот» (NLU gap) |
| claude-md-management | 1 | «обнови мозг/пуш» |
3. Outcome-распределение (после review)
| outcome_reviewed | count | % |
|---|---|---|
| soft_success | 9 | 39% |
| success | 6 | 26% |
| rework | 4 | 17% |
| blocked | 4 | 17% |
Проблемная доля 8/23 = 35% (rework+blocked). На retro #6 эта доля была ≈30%; небольшой рост.
degradedCount = 2 (классификатор был в degraded-режиме в 2 turns — нормально на старте сессии).
4. Каузальные цепочки (от → к, общие файлы)
4 цепочки выявлены автоматически:
269ae4d0 → 1b0f3090— общийsettings.json(кросс-сессионный — настройки router-gate перетряхнули, затем восстановили).1b0f3090 → 1b0f3090×3 — длинная задача внутри одной сессии 1b0f3090 (5 episodes), общийrouter-state-1b0f3090.jsonчерез все 4 turns.
Сессия 1b0f3090 — самая длинная задача периода (5 эпизодов из 7 в task ref #3+#4). Один из 5 turns — blocked (recovery «обнови мозг/пуш», 15 tool calls, 81k output tokens — reviewer пометил mistake_should_not_start).
5. Reviewer-narrative — 8 problematic episodes (детально)
| # | task | cls | outcome | reviewer error_root_cause | reviewer alt |
|---|---|---|---|---|---|
| 1 | 135a4adf | conversation | rework | external_failure (hook errors) | n/a |
| 2 | 267fd4dc | chain | rework | wrong_chain_order | #8→#3 chain skipped |
| 3 | 1b0f3090 | ambiguous | blocked | n/a (correct: ask user) | n/a |
| 4 | 267fd4dc | conversation | rework | external_failure | n/a |
| 5 | b82510c7 | ambiguous | rework | wrong_skill | #3 GitHub MCP («пуш и обнови пилот») |
| 6 | b82510c7 | no_skill_found | blocked | n/a (correct: ask user) | n/a |
| 7 | 269ae4d0 | ambiguous | blocked | wrong_skill | claude-md-management («обнови мозг/пуш» — 15 tool calls вместо clarification) |
| 8 | b11f6b8d | no_skill_found | blocked | wrong_skill | (ask user, not subagent-driven-development) |
Главный паттерн: на ambiguous/short prompts agent не просит уточнения, а пытается угадать. В 3 из 4 ambiguous/no_skill_found эпизодов это привело к ошибке.
6. Sanity-check (ответы заказчика)
| вопрос | ответ |
|---|---|
| Были моменты, когда я выбрал direct, хотя нужен был навык? | «Да, часто» |
| Качество за период (5 blocked + 2 degraded из 23)? | «Плохо — очевидные сбои» |
| Что наблюдатель должен был засечь, но не засёк? | «Вроде нет» |
Меta-расхождение: заказчик сказал «наблюдатель ничего не пропустил», но reviewer нашёл 5 wrong_skill cases. → Наблюдатель засёк, заказчик не знал. Заявка на улучшенный surface STATUS.md (см. кандидаты).
Файл ответов: docs/observer/sanity-checks/2026-05-27.json.
7. Self-retrospect trigger
docs/observer/.self-retrospect-counter.json: episodes_since_last = 542 (был 519, +23 за период). Порог 50 превышен на порядок — рекомендую запустить /self-retrospect при первом удобном моменте.
8. Cost report
~/.claude/runtime/cost-daily.json — отсутствует (cost tracking не активирован per-call). Из analyzer.costTotals:
| метрика | tokens |
|---|---|
| classifier_input | 220 |
| classifier_output | 4 431 |
| self_assessment_input | 0 (покрытие 22%) |
| self_assessment_output | 0 |
| reviewer_input | 0 (batch-reviewer не пишет в costTotals) |
| reviewer_output | 0 |
Reviewer batch off-stream cost — ≈$1.50 (23 эпизода × Opus 4.7 ≈ avg 1.5к in / 0.4к out per call).
9. Candidates for owner review
⚠️ Это кандидаты, не действия. Заказчик решает что применить.
C1 — NLU gap: транслит-сленг → не маппится в правильный навык
Сигнал: «пуш и обнови пилот» → recommended_node = NULL → direct (15 tool calls, rework). Reviewer: правильно было #3 GitHub MCP. Аналогично — «обнови мозг/пуш» (claude-md-management не вызван).
Rationale: classifier хорошо парсит формальные слова («deploy», «push»), но плохо — русский транслит-сленг («пуш», «пилот», «мозг», «эталон»). Между тем ПИЛОТ.md / ЭТАЛОН.md / обнови мозг = MEMORY.md — это формализованные паттерны заказчика (зафиксированы в MEMORY.md recovery draft).
Suggested action (one of):
- (A) Расширить prefilter словарь
tools/observer-prefilter.mjs— добавить mapping «пуш+пилот → #3+deploy», «обнови мозг → claude-md-management», «обнови эталон → file Edit ЭТАЛОН.md», «обнови пилот → file Edit ПИЛОТ.md». - (B) Добавить в classifier system-prompt список 8-10 known транслит-фраз заказчика.
- (C) Не править ничего — заказчик использует эти фразы редко, частота не оправдает усложнения.
Rejection-option: заказчик решает что транслит-NLU не приоритет; держать cls: теги в промпте как явный override.
C2 — Ambiguous/short prompts: правило «ask before start»
Сигнал: 3 из 4 ambiguous/no_skill_found эпизодов = rework/blocked. Reviewer 2× флаг mistake_should_not_start: «обнови мозг/пуш» (15 tool calls вместо clarification) и «ставь в пендинг» (subagent-driven-development вместо clarification).
Rationale: при classifier_output.task_type ∈ {ambiguous, no_skill_found} AND prompt_length < 30 chars AND нет cls: тега — почти всегда правильно спросить, а не пытаться. Сейчас agent чаще пробует угадать (один раз с 15 tool calls).
Suggested action (one of):
- (A) Hook
router-tool-gateуже блокирует наno_skill_found— расширить наambiguous + len<30тоже. - (B) Skill
clarification-request(новый, минимальный) — обязательно вызывать на ambiguous/no_skill_found+short. - (C) Дописать в
~/.claude/CLAUDE.mdправило: «на коротких ambiguous prompts — first action = AskUserQuestion».
Rejection-option: заказчик согласен с rework как ценой за скорость на коротких задачах.
C3 — Self-assessment coverage 22% (было выше)
Сигнал: 18/23 эпизодов без self_assessment (78%). На retro #6 покрытие было выше. Скорее всего сломалось при правке hook order 26.05 (commit 9b7de8bf).
Rationale: без self_assessment reviewer не может оценить «agent_self_assessment_accuracy» → теряем сигнал самооценки.
Suggested action (one of):
- (A) Найти что именно изменилось в hook order, восстановить self_assessment trigger.
- (B) Принять снижение покрытия как trade-off за упрощённый hook stack.
Rejection-option: заказчик согласен жить без self_assessment до следующего больного эпизода.
C4 — Меta: «вроде нет» от заказчика vs 5 wrong_skill от reviewer
Сигнал: заказчик не заметил wrong_skill кейсы, которые reviewer нашёл. STATUS.md не surface'ит «wrong_skill last 24h» — заказчик не видит то, что наблюдатель видит.
Rationale: brain governance ADR-011 §16 говорит «evidence-collection, not enforcement», но evidence должен быть видимым.
Suggested action (one of):
- (A)
tools/status-md-generator.mjs— добавить блок «Reviewer findings last 24h» (count wrong_skill / wrong_chain_order / external_failure). - (B) Опционально — push-notification контроллеру при
wrong_skill ≥ 3 за день. - (C) Принять, что заказчик не должен следить за этим — оставить только в /brain-retro.
Rejection-option: /brain-retro раз в неделю достаточно.
C5 — Chain #8 (gitleaks) → #3 (GitHub push) skipped
Сигнал: classifier рекомендовал chain #8→#3 (gitleaks верификация → push), agent ушёл direct, chain_quality missing_step. Reviewer: «skipping #8 verification before push is risky given pending .gitleaksignore».
Rationale: это повторяющийся паттерн (см. memory feedback_gitleaks_cross_branch.md — pre-push gitleaks уже блокировал push'и из-за cross-branch fingerprint'а; ущерб от пропуска — низкий, но регулярный).
Suggested action (one of):
- (A) Hook
enforce-verify-before-push(есть вfeedback_enforce_verify_before_push.md) — расширить на gitleaks verify timestamp. - (B) Добавить в memory entry «при push после правки нормативки/спеков — обязательно
git-leaks --stagedперед push». - (C) Принять: gitleaks pre-push уже блокирует на сервере, дублирование избыточно.
Rejection-option: существующий pre-push gitleaks достаточен.
10. Что не правится автоматически
Per skill §«Behavioral rule reminders» — этот retro никакие правки не вносит. Все 5 кандидатов выше — material for owner decision. Заказчик может выбрать «все», «никакие», «только C1+C3» — любым способом.
11. Цепочки и связи с предыдущим retro
retro #6 (2026-05-26 16:23) — закрыл проблему «classifier сломан» (NULL > 30%) фиксом G/H/A1/A2/B3/C1/C3. retro #7 подтверждает: NULL = 8.7%, классификатор здоров.
Новые проблемы которые видит retro #7:
- NLU gap на транслит — не было в retro #6 (был мёртвый классификатор, NLU маскировался).
- «ask before start» discipline — старый паттерн, продолжает.
- Self-assessment coverage drop — регрессия от retro #6 (вероятно из-за hook order правки).
- Reviewer judgments routing_judgment = NULL для всех 23 — мелочь schema-mismatch в reviewer prompt vs анализатор (reviewer использует
node_quality/error_root_causeвместоrouting_judgment); analyzer ожидает старое поле. Не требует действия — обе версии данных есть.
Подпись: контроллер Opus 4.7, 1M context, brain-retro skill v3 (subagent + batch hybrid), 2026-05-27 03:55 UTC.