Generalize the focus controller into a harness hosting swappable modes
Loosen AntiDrift's session controller into Keel's general collect→brain→act
loop. A new internal/harness runs at most one mode.Mode at a time, fanning
async completions out to the web SSE and status-bar surfaces.
- internal/mode: the Mode contract (Kind/Command/View/Active) plus optional
EvidenceConsumer and Expirer ports, and the surfacing Envelope.
- internal/mode/focus: the former session/domain/statemachine packages moved
under the mode, now satisfying the harness contracts unchanged.
- internal/mode/offscreen: a one-shot away-from-desk mode built on the new
ai.Proposer, which turns a life-domain brief into one off-screen action.
- cmd/keeld replaces cmd/antidriftd; daemon wires focus + offscreen factories
with per-mode persistence under ~/.keel/modes/<kind>.
- Finish the rename: KEEL_* env refs in the README, /keeld build artifact
ignored, stale antidriftd binary removed.
Include the design + implementation plan this refactor was built from under
docs/superpowers/{specs,plans}/2026-06-04-controller-refactor*.md.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -9,27 +9,37 @@ effectors — surfaced on a web UI and the WM status bar. The brain, the storage
|
||||
> **Architecture:** [`docs/keel-architecture.md`](docs/keel-architecture.md) is the
|
||||
> source of truth. **Agents:** read [`AGENTS.md`](AGENTS.md) first.
|
||||
|
||||
## Focus mode (AntiDrift)
|
||||
## Modes
|
||||
|
||||
What runs in this repo *today* is **AntiDrift**, Keel's first mode: a personal
|
||||
focus operating system that treats each work session as an explicit commitment
|
||||
(next action, success condition, timebox) and makes drift visible. Keel
|
||||
generalizes its controller so a focus-session becomes one mode among several
|
||||
(house, body, review, capture). The milestone history below is this mode's record.
|
||||
Keel's controller is now a generic **harness** that hosts one *mode* at a time,
|
||||
and the daemon ships two:
|
||||
|
||||
> **Naming:** the directory and git repo are renamed to `keel`; the *code identity*
|
||||
> is intentionally still `antidrift` (Go module, `antidriftd` binary, `~/.antidrift/`
|
||||
> runtime, `ANTIDRIFT_*` env). The code rename lands with a state migration during
|
||||
> the controller refactor — see `docs/keel-architecture.md` §8.
|
||||
- **Focus (AntiDrift)** — Keel's first mode: a personal focus operating system
|
||||
that treats each work session as an explicit commitment (next action, success
|
||||
condition, timebox) and makes drift visible. The milestone history below is
|
||||
this mode's record.
|
||||
- **Off-screen** — an away-from-the-desk mode: it reads today's Marvin tasks plus
|
||||
the `~/owc` goals and life-domain `bug-*.md` notes, asks the brain for one
|
||||
worthwhile off-screen action, and on confirm files it as a Marvin task.
|
||||
|
||||
When no mode is active the web UI shows a **launcher** to start either one.
|
||||
Further modes (body, review, capture) are aspirational. The milestone history
|
||||
below records the focus mode's development.
|
||||
|
||||
> **Naming:** the rename is complete — directory, repo, Go module, binary,
|
||||
> runtime, and env are all `keel` (`keeld` binary, `~/.keel/` runtime,
|
||||
> `KEEL_*` env). If you have a live ledger under the old `~/.antidrift/`
|
||||
> directory, move it manually to `~/.keel/`.
|
||||
|
||||
## Run
|
||||
|
||||
```bash
|
||||
go run ./cmd/antidriftd
|
||||
go run ./cmd/keeld
|
||||
```
|
||||
|
||||
The daemon serves a local web UI at http://localhost:7777 and opens your
|
||||
browser. State is persisted to `~/.antidrift/state.json`.
|
||||
browser. Per-mode state is persisted under `~/.keel/modes/<kind>/` (e.g.
|
||||
`~/.keel/modes/focus/state.json`).
|
||||
|
||||
## Test
|
||||
|
||||
@@ -57,8 +67,8 @@ into the coach's grounding; the reflection lines are short and cross the wire
|
||||
by design, while the knowledge profile still does not.
|
||||
|
||||
M6 (knowledge port): the planning coach now sharpens intents against who you
|
||||
actually are. A single profile file (`~/.antidrift/knowledge.md`, overridable
|
||||
via `ANTIDRIFT_KNOWLEDGE_FILE`) holds your standing context — priorities,
|
||||
actually are. A single profile file (`~/.keel/knowledge.md`, overridable
|
||||
via `KEEL_KNOWLEDGE_FILE`) holds your standing context — priorities,
|
||||
values, what counts as good work — and the daemon loads it asynchronously on
|
||||
entering planning, mirroring the tasks fetch. The cached text grounds the AI
|
||||
coach prompt only; the drift judge and nudge are untouched, and the profile text
|
||||
@@ -86,7 +96,7 @@ The drift judge degrades gracefully — without it, local matching still runs.
|
||||
|
||||
M2 (AI planning coach): in the Planning view, a rough intent is "sharpened"
|
||||
into a structured commitment (next action, success condition, timebox) by an
|
||||
LLM CLI backend (claude or codex, selectable via `ANTIDRIFT_AI_BACKEND`). The
|
||||
LLM CLI backend (claude or codex, selectable via `KEEL_AI_BACKEND`). The
|
||||
coach runs asynchronously and degrades gracefully — manual planning always
|
||||
works.
|
||||
|
||||
|
||||
Reference in New Issue
Block a user