08b5c63a0f
Backlog hygiene per the file's own maintenance rule — resolved items get
moved out, not left ticked-in-place.
- Cut resolved body bullets from BACKLOG §A/B/C/D/E/G/I (health probes,
static-first infra, CritiqueFinding, architect contradiction-check, A1/A2
gates, batch fetch-approval, source/egress events, render matrix, markdown,
session list, idea promotion, turnId/probe/narration, .cs symbols, scene
validator). All already archived in RETRO's burndown table.
- Narrow partially-done items to their live follow-up rather than delete:
B5 -> static_check stage emitter only; B6/C-A3 -> CritiqueOutcomeCorrelated
producer only; C-A1 -> planner-prompt activation only.
- Drop the stale "§E UNBLOCKED" index line (plan-comparison is BLOCKED, no
PlanCandidate event; idea-promotion shipped f107ff5).
- Archive the operator-requested TUI wave (palette, @ picker, CLAUDE.md L0
injection, inline action rows, free-scroll/help/filter) in RETRO 2026-06-22
— never BACKLOG items, would otherwise be orphaned in neither file.
- gitignore apps/tui-go/preview (cmd/preview build artifact).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
108 lines
12 KiB
Markdown
108 lines
12 KiB
Markdown
# CORREX — RETRO (archive of resolved BACKLOG items)
|
|
|
|
Counterpart to `BACKLOG.md` (the live outstanding list). Items here are **built and
|
|
unit-verified** (Gradle green). Where a live-QA gate applies, that's called out as a
|
|
follow-up — this sandbox has no local model / SearXNG / GPU / network, so live-QA
|
|
could not be run here.
|
|
|
|
---
|
|
|
|
## 2026-06-22 — BACKLOG hygiene reconcile + operator-requested TUI wave (branch `feat/backlog-burndown`)
|
|
|
|
**Hygiene reconcile.** Per `BACKLOG.md`'s own maintenance rule, cut the resolved body bullets
|
|
that were left ticked-but-in-place after the 2026-06-20 burndown and 2026-06-21 grants work.
|
|
Sections affected: §A (health probes), §B (static-first infra, `CritiqueFinding`, architect
|
|
contradiction-check), §C (A1/A2 gate code), §D (batch fetch-approval, source events, dynamic
|
|
egress), §E (render matrix, markdown, session list, idea promotion), §G (turnId/probe/narration),
|
|
§I (`.cs` symbols, scene validator). Partially-done items were **narrowed to their live
|
|
follow-up** rather than deleted: §B5 → "static_check stage emitter only", §B6/§C-A3 → "the
|
|
`CritiqueOutcomeCorrelatedEvent` producer only", §C-A1 → "planner-prompt activation only". The
|
|
full commit map stays in the BACKLOG "✅ RESOLVED" index; detail is in the tables below.
|
|
|
|
**Operator-requested TUI wave (archived here — never BACKLOG items, like the grants work).**
|
|
A run of TUI/UX features added on the branch after the burndown, each compiled + `go vet`/`go
|
|
test` green and rendered via `cmd/preview` before commit:
|
|
|
|
| Commit | What |
|
|
|--------|------|
|
|
| `9143d55` | Global input history + stop idle redraws (copy-safe — no redraw churn while selecting text). |
|
|
| `85bfddf` | Slash-command menu in the chat input. |
|
|
| `2662156` | Transparent modal backdrops (overlays no longer paint an opaque box over the transcript). |
|
|
| `ba7ac06` | Transcript message-jump (`^↑`/`^↓` to your prev/next message) + OSC52 clipboard copy. |
|
|
| `65e5d88` | **Server:** `ListFiles`/`FileList` protocol backing the TUI `@` picker. |
|
|
| `04d7e26` | `@` file-reference picker in the input. |
|
|
| `c616982` | **Context:** inject `CLAUDE.md` / `AGENTS.md` as L0 standing context. |
|
|
| `54f94a5` | Command-palette keybinds + configurable (hideable) status bar. |
|
|
| `6a06f2e` | Inline action rows in the OUTPUT transcript (tool results / approvals / writes / grants as `RouterEntry` role `action`, interleaved by arrival). |
|
|
| `f14a83c` | Drop the inline tool-*start* rows (they doubled up with the result rows). |
|
|
| `531910d` | Transcript free-scroll (`PgUp/PgDn`, `^u/^d`, `esc` snaps to tail-follow; clamped via `outputViewport()`/`buildTranscriptRows`, 2 tests) + help overlay (`?`) + event-inspector `/` filter. |
|
|
|
|
These are mostly deterministic render/UX changes (verifiable by `go test` + `cmd/preview`); the
|
|
only remaining live look is the §E approval-ergonomics re-audit noted in BACKLOG (the band gained
|
|
the grant scope-picker + action rows since `d5afcd3`).
|
|
|
|
---
|
|
|
|
## 2026-06-21 — wider grants + revoke (branch `feat/backlog-burndown`)
|
|
|
|
Operator-requested (not a prior BACKLOG item): grants that outlive a single session, plus a
|
|
revoke path. Two commits, each compiled + unit-tested green.
|
|
|
|
| Commit | What |
|
|
|--------|------|
|
|
| `c36d41b` | **Cross-session grant scopes (PROJECT/GLOBAL) + revoke.** `GrantScope.GLOBAL(toolName)` added; `PROJECT` made tool-bound. Engine `scopeMatches`: GLOBAL matches the bound tool anywhere, PROJECT when the session's `projectId` (derived from the bound workspace root via `ProjectIdentity.of`) AND tool match. New reserved `GRANT_LEDGER_SESSION_ID` stream holds PROJECT/GLOBAL grants; the approval gate unions the ledger's grants with the session's. `RevokeGrant` → `ApprovalGrantExpiredEvent` on the ledger (reducer already drops it); `ListGrants`/`GrantList` expose the active standing grants. **Server-side T2 grant ceiling removed** per operator request — a grant may now authorize any tier (incl. T3/T4); tool-binding is the remaining guard. New `GrantScopeMatchingTest` (5). |
|
|
| `8df0ec7` | **TUI: scope picker (A) + standing-grants viewer.** `A` (approve-always) opens a session/project/global picker (SESSION default = old behaviour); `p`/`g` create wider grants. `grants` palette command + `G` shortcut open `OverlayGrants` listing scope/tool/tiers/path with `x`/enter to revoke. `protocol.go`: `TypeGrantList`+`GrantDto`, `RevokeGrant`/`ListGrants` encoders. Both overlays rendered via `cmd/preview` (kinds `grants`, `grant-scope`). |
|
|
|
|
**Why the design:** session grants are event-sourced per-session and die with the session;
|
|
project/global grants must outlive any one session, so they live in a dedicated ledger stream
|
|
the gate folds in — keeps grants in the audit log (invariant #9) rather than config.
|
|
|
|
**⚠️ Live-QA gate (move out of RETRO once passed):** unit tests cover the engine matching,
|
|
reducer, and ledger fold, but the *cross-session* behaviour — create a GLOBAL/PROJECT grant in
|
|
session A, confirm a **different** session B auto-clears that tool, then revoke and confirm it
|
|
prompts again — needs a running server + model. Not runnable in this sandbox.
|
|
|
|
---
|
|
|
|
## 2026-06-20 — backlog burndown (branch `feat/backlog-burndown`)
|
|
|
|
Nine tracks, each compiled + unit-tested green before commit.
|
|
|
|
| Commit | Track | BACKLOG ref |
|
|
|--------|-------|-------------|
|
|
| `f783eed` | `CritiqueFinding`/`CritiqueSeverity`/`CritiqueRole` type + `CritiqueOutcomeCorrelatedEvent` + `core/critique` calibration projection (state/reducer/projector) | B §6 + C-A3 |
|
|
| `784accb` | `repomap:` turnId namespace requires trailing `:` (no `/repo`↔`/repo2` collision; L3RepoKnowledgeRetriever filter + ProjectMemoryService write) + WorkspaceStateProbe newline fingerprint | G |
|
|
| `266bbf0` | `EventStoreLatencyProbe` (wired) + `LlamaServerHealthProbe` (+ injectable `LlamaLivenessClient`) + `HealthConfig.eventStoreWarnLatencyMs` | A §4 |
|
|
| `f715ffa` | `.cs` / Godot-Mono type symbols in `RepoMapIndexer.SYMBOL_PATTERNS` | I |
|
|
| `0e251d6` | `SceneValidator` — structural `.tscn`/`.tres` (header well-formedness, ExtResource/SubResource id resolution, node parent integrity) | I |
|
|
| `1df7af5` | Brief echo-back gate: `BriefEchoMismatchEvent` + `BriefEchoComparator`/`BriefEchoExtractor` + `checkBriefEcho` orchestrator gate | C-A1 |
|
|
| `1a1b5cc` | Stage-level plan checkpointing: `StageCheckpointPassed/FailedEvent` + `StageCheckpointReconciler` + `emitStageCheckpoint` (gated on a locked plan) | C-A2 |
|
|
| `eae0a0c` | Architect contradiction-check (display-only): `PossibleContradictionFlaggedEvent` + L3-backed `ArchitectContradictionChecker` | B §4 |
|
|
| `b098d87` | Dedicated `SourceFetchedEvent` / `LowQualityExtractionEvent` (promoted from `ToolExecutionCompletedEvent` metadata; additive), emitted from `SandboxedToolExecutor` | D |
|
|
| `027ff1f` | Dynamic per-session egress allowlist: `EgressHostsGrantedEvent` + `EgressAllowlist` union helper + `EgressAllowlistProjection`; `NetworkHostRule` delegates to the union | D |
|
|
| `447fc7a` | Reviewer static-first: `StaticFindingsRecordedEvent` + `StaticAnalysisRunner` (injectable `CommandRunner`; compiler/ktlint/detekt parsers) + `excludeStaticFindingsFromReview` filter, live-wired into reviewer context assembly | B §5 |
|
|
| `eff8f8d` | Narration-lane lag: stale pause narrations dropped per-approval-request on resolve / per-session on resume (replay-safe) | G |
|
|
| `1e6699a` | tui-go `go.mod` `go 1.26` → `1.24.2` (1.26 toolchain unreleased/unfetchable) — unblocks Go build/test on released toolchains | E (enabler) |
|
|
| `da72ee5` | tui-go: markdown rendering for chat turns via `glamour` (dark, per-width memoized), plain-text fallback; other roles/UI untouched | E |
|
|
| `1f7a5d9` | tui-go session list / resume view: `R` overlay over `GET /sessions`, resume via `POST /sessions/{id}/resume` onto the existing global stream | E |
|
|
| `2a99e15` | tui-go per-event render-matrix golden tests (37 cases) + a coverage guard that parses `protocol.go` so any new event type without a golden fails | E §2 |
|
|
| `d5afcd3` | tui-go approval ergonomics: navigable pending-approval queue (no modal stacking) + `y/n/e` keys + tier-gated T3+ arm/confirm | E §3 |
|
|
| `641051b` | Plan-derived diff manifest: `PlanStage.writes` + `PlanDerivedManifest.deriveAllowedWrites`/`combine`, unioned into `StageConfig.writeManifest` at compile, enforced by the existing containment matcher | B §2 |
|
|
| `ab7e4be` | Egress allowlist **activation**: `resolveSessionEgressHosts` threads the session's `EgressAllowlistProjection` state into `ToolCallAssessmentInput` at `runPlane2Assessment`, so `NetworkHostRule` now consults the live per-session union (was fed `emptySet()`) | D (activation) |
|
|
| `4b0024f` | Batch source-list fetch-approval: `POST /sessions/{id}/approve-sources` → `SourceListHosts.extract` (java.net.URI, lower-cased, ports stripped, dossier-line tolerant) → one `EgressHostsGrantedEvent`; live allowlist then auto-clears those web_fetches (no per-URL T2) | D |
|
|
| `f107ff5` | Idea-board → project-profile promotion: `IdeaPromotedEvent` (board tombstone, like discard) + `ProjectProfileWriter` (escape-aware TOML serialize/write) + `ProjectProfile.withConvention` (deduped) + server `PromoteIdea` handler (loads profile, appends idea text, writes `.correx/project.toml`); also made `SimpleToml`'s reader unescape `\\`/`\"` symmetrically with the writers (fixes pre-existing read/write asymmetry) | E |
|
|
| `4e08510` | Architect contradiction-check **activation**: `ServerModule.start()` subscribes to the architect stage's `design` `ArtifactCreatedEvent`, resolves decision text (design-schema `approach` field, capped fallback), runs `ArchitectContradictionChecker.check`, appends the non-null `PossibleContradictionFlaggedEvent`. Live-only, never halts. Checker built in `Main.kt` (gated on `project.enabled`) and threaded into `ServerModule`. Replaces the `Main.kt` `TODO(wiring)` | B §4 (activation) |
|
|
| `64a90e7` | Llama-probe **registration**: `LlamaServerHealthProbe` (266bbf0) wired into the health monitor when a `llamacpp` provider URL is configured — dedicated CIO client (3s timeout, shutdown-hook close) + `HttpLlamaLivenessClient`. Gated so a model-less box reports no spurious `LLAMA_SERVER` DEGRADED. Replaces the `Main.kt` `TODO(wiring)` | A §4 (activation) |
|
|
|
|
### Follow-ups created this pass (refiled into BACKLOG)
|
|
- **C-A1 activation** — `planner.md` must emit a `brief_echo` block and `role_pipeline.toml` must set `briefEcho="true"` / `briefEchoSource` for the gate to fire live (model-dependent → live-QA).
|
|
- **C-A3 producer** — nothing emits `CritiqueOutcomeCorrelatedEvent` yet; the calibration projection has no live feed until a reviewer-loop producer records finding outcomes.
|
|
- **B §4 wiring** — ✅ DONE (`4e08510`): `ServerModule.start()` now subscribes to the architect `design` artifact and emits the flag. (In-session L3 embedding is NOT needed — the checker filters to PRIOR sessions by design, so it works against prior runs' distilled decisions.)
|
|
- **A §4 llama wiring** — ✅ DONE (`64a90e7`): the probe is registered in the health monitor (gated on a configured `llamacpp` provider URL) via `HttpLlamaLivenessClient`. (tokens/sec telemetry still rides liveness-only — the `/health` endpoint reports reachability; a throughput feed remains future work but the spec's liveness probe is live.)
|
|
- **D egress wiring** — ✅ DONE (`ab7e4be`): session egress state is now threaded into `ToolCallAssessmentInput` at `runPlane2Assessment`, so `NetworkHostRule` consults the live union. Batch fetch-approval ✅ DONE (`4b0024f`): `POST /sessions/{id}/approve-sources` emits one `EgressHostsGrantedEvent` for the whole source list.
|
|
- **B §5 static_check stage** — runner/event/filter complete and the filter is live, but no workflow stage emits `StaticFindingsRecordedEvent` yet (`// TODO(wiring)` in `StaticAnalysisRunner.kt`); needs an event-emitting deterministic stage-type seam.
|
|
- **E toolchain** — tui-go now builds via auto-downloaded go1.24.2 (`GOTOOLCHAIN=auto`). The committed directive fix assumes 1.26 was unintended; bump if a specific newer release is actually wanted.
|
|
|
|
### Environment note
|
|
- A `~/.gradle/gradle.properties` machine-local override was added on this box (`-Xmx768m`, `parallel=false`, kotlin daemon `-Xmx640m`) because the repo's `-Xmx4G` OOM-killed the foreground process on a 1.9 GB machine. **Not committed** — repo defaults intact for higher-RAM machines.
|