Files
ClaudeDo/docs/verification-handoff.md
T

11 KiB
Raw Blame History

Verifikations-Handoff (2026-07-23)

Konsolidierte manuelle Verifikationen aus docs/open.md + Memory-Ständen — gedacht für eine frische Session, die diese Punkte am laufenden System durchspielt. Mika bedient die UI, die Session protokolliert Pass/Fail.

Vorbedingungen: Worker + App laufen (SignalR-Port lt. ~/.todo-app/worker.config.json, aktuell 37821; External MCP 47822). Testliste ClaudeDoTests (C:\TestRepos\ClaudeDoTests) für zerstörungsfreie Runs nutzen.

Achtung: 7 Bugfix-/Chore-Tasks vom 2026-07-23 (createdBy claude-code-gap-analysis) liegen in der Queue der Liste „Claude do". Die Merge-bezogenen Checks (Abschnitte 2 und 4) erst NACH Review/Merge dieser Tasks final abhaken — sie ändern ggf. genau dieses Verhalten.

Nacharbeit: Erledigtes aus docs/open.md austragen, dieses File danach löschen.


1. Detail-Insel & Diff-Viewer (reines Durchklicken)

  • [~] Detail-Insel komplett: Output/Git/Session-Tabs, Merge-Sektion, Agent-Settings-Overrides (InheritedBadge korrekt), Prep-Panel — nach dem VM-Split (DetailsIslandViewModel → Sektions-VMs) alles gebunden, keine leeren Panels. — TEILWEISE (2026-07-24, User-Sichtprüfung an verif §1 diff matrix): Output/Git-Tabs, Merge-Sektion, Agent-Badges vorhanden & gebunden, keine leeren Panels. Git-Tab: +1 37, „merges cleanly" korrekt. BUG: OUTCOME-Karte zeigt rohes JSON (s. open.md). Session-Tab fehlt — erwartet (nur bei Parent mit Kindern, HasChildOutcomes; wird in §4/§3 mit echtem Parent geprüft). Minor: TurnsText 0/max bei terminalem Reload (open.md). Prep-Panel → §10.
  • [~] Diff-Viewer: Dateiliste, Added/Deleted/Renamed/Binary-Erkennung, Commit-Range-Diff nach einem Merge. — Added/Deleted/Binary PASS; Renamed erkannt + „R"-Badge, aber schwach dargestellt (kein alt→neu-Pfad, „+0 0" — nit, s. open.md); „Review Combined Diff" korrekt ausgegraut (kein Planning-Parent). Commit-Range-Diff nach Merge: PASS (2026-07-24) — Diff des gemergten Done-Tasks rendert über base..head trotz entferntem Worktree.
  • DiffModal-Fehler-State: Commit-Range ohne aufgezeichnete Commits → „Diff nicht mehr verfügbar" statt Crash/leer. — offen (nach Merge).
  • „children need attention"-Band auf dem Session-Tab eines Parents mit failed/blocked Kind. — verschoben nach §3 (braucht echten Parent mit Kindern).

2. Worktree-Pipeline (3 falsifizierbare Fälle)

  • Happy-Path: Task mit WorkingDir → worktrees.state='active', head_commit gesetzt, diff_stat non-empty, Branch claudedo/<id[:8]> existiert auf Disk. — PASS (2026-07-24) via Task e63eb2f5 (sonnet): Worktree active, headCommit 8a3ae86 (ahead=1 vom Base), diff_stat non-empty (review-cancel.txt), Branch claudedo/e63eb2f5… auf Disk. (Mein erster Versuch mit model=haiku schlug fehl — das war ein haiku/auto-Footgun, keine Pipeline-Sache; s. open.md.)
  • No-Changes-Run: → status='Done', head_commit IS NULL, diff_stat IS NULL. — PASS (2026-07-24); Präzisierung: aktueller Flow endet in WaitingForReview (nicht Done, das ist erst nach Approve) — Doc-„Done" ist veraltet. Kein neuer Commit, leerer Diff bestätigt.
  • Kein Git-Repo (WorkingDir = C:\Temp): → status='Failed', KEINE worktrees-Row, Git-Fehler im Log. — PASS (2026-07-24); Fehler: „Worktree creation failed: working_dir is not a git repository".

3. Planning-Flow-Walkthrough

  • Draft → Finalize → Kette: Finalize queued NICHT automatisch (Kinder bleiben Idle); „Queue plan" setzt alle nicht-terminalen Kinder Queued, Kette läuft sequenziell durch (blocked-by löst sich je Vorgänger).
  • Parent landet nach letztem terminalen Kind in WaitingForReview; Approve merged die ganze Unit (Parent-Worktree falls Active + jedes Done-Kind in Reihenfolge).
  • UnfinishedPlanning-Modal: Resume / FinalizeNow / Discard.

4. Merge-Editor (Rider-Style 3-Pane) mit echtem Konflikt

Konflikt provozieren: gleiche Datei auf main ändern, während der Task-Branch sie ändert. Beide Wege testen: (a) Single-Task-Approve mit Konflikt, (b) Planning-Unit-Merge mit Konflikt in einem Subtask (PlanningMergeConflict → Editor öffnet pro Subtask).

Verifiziert 2026-07-24 (Single-Task-Approve mit Konflikt, 2 Dateien, verif §4): End-to-End PASS — Approve→Konflikt→3-Pane-Resolver→beide Dateien auflösen→Continue→Merge→Task Done (Merge-Commit gelandet). Sauberer additiver Approve (verif §1b, kein Konflikt) → direkt gemergt → Done, kein Editor: PASS (2026-07-24). ⚠ Vorbedingung-Fund: ein dirty Ziel-Working-Tree (getrackte uncommittete Änderung) blockt den Merge und Approve schluckt das still (s. open.md „Approve & Merge schluckt blocked"). Planning-Unit-Merge-Konflikt (Weg b) noch offen → §3.

  • Drei Panes: MAIN read-only | Result editierbar | INCOMING read-only; Konfliktblöcke rot, aufgelöst grün, in allen Panes. — PASS.
  • Gutter-Toggle /: Seite rein/raus, Klickreihenfolge = Reihenfolge im Result; main/incoming/beide/keine möglich. — PASS.
  • Nur Konfliktregionen im Result editierbar (Stable read-only); Edits fließen in den Block zurück. — PASS.
  • [~] Synchrones vertikales Scrollen; File-Switcher bei mehreren Dateien; M conflicts · K resolved-Readout; Conflict-Ruler (Klick springt). — PASS, aber Multi-File schlecht erkennbar (2 Konfliktdateien schwer zu sehen — UX-Nit, open.md).
  • [~] Continue erst aktiv, wenn ALLE Konflikte in ALLEN Dateien gelöst; Binär-Guard greift. — funktional PASS (merged erst nach Auflösung beider Dateien), aber Button ist klickbar statt disabled solange offen → stummer No-op (UX-Bug, open.md). Binär-Guard hier n/a.
  • Abort: Tree sauber, Task bleibt WaitingForReview. — nicht getestet (User wählte Continue/Merge). Offen.
  • [FEATURE-WUNSCH] farbliches Hervorheben der übernommenen/eingefügten Zeilen im Result-Pane (open.md).
  • Bekannte Kanten (nur gegenprüfen, nicht als Fail werten): leere Ours-Seite → null-lange Result-Region (Accept geht, Handtippen fummelig); Gutter-Y-Ausrichtung bei sehr hohen Fenstern/großem Scroll; vertikaler Drift nachfolgender Blöcke nach Konflikt mit ungleicher Zeilenzahl.

5. Embedded ConPTY / Mission Control

  • Kritisch: Task-basiert (Kontextmenü „Open ConPTY session"): frischer Task → Worktree wird on-demand angelegt, claude startet — verifizieren, dass der Task-Prompt wirklich GESENDET wird (Antwort beginnt), nicht nur im Eingabefeld vorbefüllt ist.
  • Ad-hoc: „New session"-Button → Ordnerwahl → freie Session im gewählten Verzeichnis.
  • Grid↔Tabs-Toggle; Close killt den Prozess + entfernt die Kachel; mehrere Sessions parallel; Pane-Resize reflowt das TUI.
  • Resume: im Worktree-Dir per claude --continue möglich (ClaudeDo persistiert die ConPTY-Session-Id bewusst nicht).

6. Pick up in terminal

  • Sichtbarkeit: Kontextmenü-Eintrag + Terminal-Button (ArrowOut) NUR bei WaitingForReview und Failed; bei Idle/Running/Queued/Done nicht. — PASS (2026-07-24, Code+Test): CanPickUpInTerminal => Status is WaitingForReview or Failed (TaskRowViewModel.cs:69, DetailsIslandViewModel.cs:898), gebunden in TaskRowView.axaml:56 + TaskHeaderBar.axaml:34, Notify bei Statuswechsel, Unit-Test CanPickUpInTerminal_OnlyForReviewOrFailed. (Klick→Terminal + Fehler-Surfacing bleiben manueller UI/CLI-Check.)
  • Klick → neues Windows-Terminal im Worktree-Verzeichnis, claude --resume <id> nimmt die Session mit Kontext wieder auf.
  • Fehlerfälle surfacen sauber (Footer-Strip bzw. Fehlerdialog): laufende/gequeuete Task, keine persistierte Session-Id, kein aktiver Worktree.
  • Bekannte Kante: parked-Idle (reject-park) hat oft Session+Worktree, zeigt die Aktion aber bewusst NICHT (Idle nicht unterscheidbar). Nervt das in der Praxis → CanPickUpInTerminal erweitern.

7. AskUser (Frage aus laufendem Task)

  • Task, dessen Prompt eine Rückfrage erzwingt → Frage erscheint im Task-Monitor (Mission Control), Prozess wartet.
  • Antwort inline absenden → Run läuft mit der Antwort weiter.
  • Timeout-/Cleanup-Verhalten der PendingQuestionRegistry (Frage unbeantwortet lassen): Task schlägt kontrolliert fehl, UI räumt die Frage auf (MCP_TOOL_TIMEOUT-Gotcha).

8. Session Skills (E2E + UI)

  • Settings → Skills: https://github.com/DietrichGebert/ponytail installieren → 6 Skills erscheinen (ponytail, -help, -review, -audit, -debt, -gain), auf Commit gepinnt, Dateien unter ~/.todo-app/session-skills/<name>/.
  • Skill per-Task (Agent-Settings-Flyout) oder global aktivieren → Task laufen lassen → im Worktree liegt .claude/skills/<name>/, Agent kann ihn nutzen, git status im Worktree bleibt sauber (info/exclude greift).
  • Gegenprobe: nicht-aktivierte/andere interaktive Session sieht den Skill NICHT (kein Leak nach ~/.claude).
  • UI: Skills-Tab (Install-Zeile, Karten mit Update/Remove), Checkbox-Listen im General-Tab + AgentConfigEditor (Flyout-Höhe!), leerer Zustand (0 Skills — Empty-State fehlt evtl., dann entscheiden), lange Namen/URLs (Trimming).

9. Attachments (Drag & Drop + MCP)

  • Drop aufs Detail-Pane: „Drop to attach"-Overlay, Datei erscheint in der Liste, landet unter ~/.todo-app/attachments/<taskId>/; „Add file…"-Picker; Remove-Button.
  • ComposedPreview enthält die Attachment-Pfade („## Reference files"). — PASS (2026-07-24, Code+Test): TaskPromptComposer.cs:31 emittiert „## Reference files", ComposedPreview reicht Pfade durch, TaskRunner.cs:132 injiziert zur Laufzeit; TaskPromptComposerTests decken es ab.
  • MCP: add_task_attachment / list_task_attachments / remove_task_attachment; Running-Task verweigert add/remove. — PASS (2026-07-24) für add/list/remove-Round-Trip inkl. Datei unter ~/.todo-app/attachments/<taskId>/ (71 B, korrekt, nach Remove weg). Running-Task-Verweigerung ist code-guarded (AttachmentMcpTools), aber ohne dauerhaft laufende Task nicht live geprüft → manueller Rest.

10. Daily Prep (Prime) & Weekly Report

  • Prime-Trigger: Schedule feuert bzw. „Plan day" manuell → Prep-Log streamt live, daily-prep.log enthält letzten Run, MyDay-Auswahl respektiert DailyPrepMaxTasks.
  • Weekly Report: Range-Default „seit letztem Standup-Wochentag → heute", Markdown rendert, Cache pro Range.

11. Self-Update & Autostart (am Gerät)

  • Update-Banner → Update durchführen → danach „up to date".
  • Autostart: Logoff/Logon startet den Worker (Startup-.lnk); Update-Pfad erhält den Autostart; Uninstall entfernt die .lnk.

12. Status-Bar / RunNow (Mini-Codecheck, erst messen)

  • Worker trennen/verbinden → prüfen, ob RunNow-Enable pro Task-Row sauber re-evaluiert (Connection-State lebt in IslandsShellViewModel). Nur fixen, wenn tatsächlich kaputt. — PASS/moot (2026-07-24, Code): Es gibt kein per-Row-RunNow-Control in der UI; RunNowAsync (IWorkerClient/WorkerClient) hat keinen VM/View-Aufrufer (RunNow nur via MCP run_task_now). Die realen Detail-Pane-Aktionen (Enqueue/Dequeue/Continue/ResetAndRetry) re-evaluieren korrekt bei Connection-Change (DetailsIslandViewModel.cs:317-323). Nebenbefund: RunNowAsync in der UI ist toter Code.