progress+roadmap: sync with third-session work, mark stale items

PROGRESS.md:
- remove Kuma from 'Wired but needs deploy' (key wired in eda434f)
- remove cold-start unlock from 'Not built yet' (built in b0932a1+15fe7bb)
- add third-session block: cold-start unlock, conversation depth,
  routing+persona — with the cold-start test gap called out
- update gap #2: anaphora + cross-intent landed (05236ad)
- update gap #6: note download-embedder + query_min_score knob
- remove 'Personality prompt' from Future (landed in b7eb53a)
- add caveat: cold-start unlock tests missing (3 required cases absent)

ROADMAP.md:
- add Status line under every item header with commit SHAs + verdict
- summary table gains a Status column
- replace stale 'Recommended order' with 'Remaining work' priority list
This commit is contained in:
kami
2026-07-06 14:40:18 +04:00
parent 5d1850c203
commit fe2903e878
2 changed files with 152 additions and 41 deletions
+92 -23
View File
@@ -27,6 +27,11 @@ that unlock already-built features. Highest ROI per minute on the list.
### 1.1 Kuma API key for `service_down` polling
**Status:** done (`eda434f`, 2026-07-06). Key `uk5_mavpoll-key` created, wired
into mavpoll. Agent caught a real bug: kuma expects the key as the *password*
field, not username. mavpoll switched to `network_mode: host` (compose bridge
couldn't reach localhost netdata/kuma).
**Vikunja:** #16 (prio 2)
**Est:** ~5 min
**Deps:** none
@@ -58,6 +63,9 @@ The ServiceDownRule then fires a sev4 nudge through the normal dispatcher.
### 1.2 Voice bind verification + stale comment fix
**Status:** done (`eda434f`, 2026-07-06). Stale comment replaced with verified
note. `nc -z` confirmed mavweb reaches `mavend:9100` cross-container.
**Vikunja:** #18 (prio 2)
**Est:** ~30 min
**Deps:** none
@@ -90,6 +98,12 @@ fixed. Update PROGRESS.md "Ops footnote" (line 284-286) to "verified."
### 1.3 Deploy desk_active presence script on desk PC
**Status:** not done. Script exists (`scripts/desk-active.sh`, complete) but
the systemd user timer + hypridle listener were not installed on the desk PC
(`linux`). This is an operator action on a different machine — the agent
couldn't reach it from the homesrv context. 0 facts ever written; `/dash`
presence still runs on `page_heartbeat` alone.
**Vikunja:** #15 (prio 3)
**Est:** ~1 h
**Deps:** none (the script is complete; this is a workstation deploy)
@@ -153,6 +167,16 @@ Presence is now 2 signals (desk_active + page_heartbeat) instead of 1.
### 2.1 Cold-start unlock (passkey → L3 key seam)
**Status:** code done, **tests missing** (`b0932a1` + `15fe7bb`, 2026-07-06).
`internal/webauthn/keywrap.go` (HKDF-SHA256 + AES-256-GCM, stdlib-only),
locked-mode boot in `cmd/mavend/main.go` (`lockedAPI` stub, `srv.Check`
allowlist), `MethodStoreEncryptionKey`/`MethodUnlock` IPC, mavweb
`RegisterFinish` wraps + `AssertFinish` unlocks. Env-key fallback preserved.
**Gap:** the roadmap's done-when #4 required three new test cases
(wrap/unwrap round-trip, wrong-cred unwrap fails, locked-mode IPC rejects
non-unlock methods) — none were written. `make test` is green by omission,
not coverage. Write these before relying on the cold-start path with real keys.
**Vikunja:** #14 (prio 2)
**Est:** ~1 day
**Deps:** none (the seam is documented in code comments, just not wired)
@@ -276,6 +300,15 @@ architecture item, not a config tweak.
### 3.1 Always-on listening (wake word + ambient capture)
**Status:** MVP (`e57647c` + `5d1850c`, 2026-07-06). `cmd/mavwaked/` (main +
vad + vad_test, 10 `-race` tests) ships as **energy-VAD only, no wake-word
model** — every utterance fires. `SurfaceVoice` (L0) caps it. 30ms/16kHz
frame shape matches silero-vad ONNX input 1:1, so the wake-word swap is a
local change in `vad.go`. Hardware topology settled: client box with mic
(desk PC / pi), not homesrv. mavwaked is a client binary (systemd user unit),
not a docker daemon — the agent first added it to Docker, then reverted
(`5d1850c`). Remaining: wake-word model (openWakeWord / silero-vad ONNX).
**Est:** 1-2 weeks + hardware
**Deps:** a capture device (USB mic or a dedicated ESP32-S3 box)
@@ -360,6 +393,14 @@ device); the hardware changes the deploy.
### 3.2 Conversation depth (multi-turn dialogue)
**Status:** done (`05236ad`, 2026-07-06). Path 1 (rule-based deepening)
implemented: `AnaphoraResolver` in `router/slots.go` (RU pronouns:
это/он/она/оно/тот/мой + inflections), `followUpMerge` extended for
cross-intent (Query/Fact/Reminder after Fact with anaphora inherits key +
time), `Session.History []Turn` added, fact-by-key lookup in `applyAction`.
7 new test cases including the exact done-when scenarios. Path 2 (LLM
dialogue manager) remains future — the sub-1B phraser can't drive it.
**Est:** 3-5 days
**Deps:** none (the dialogue scaffold is wired; this deepens it)
@@ -425,6 +466,9 @@ test` green with the new cases.
### 3.3 Latency / streaming
**Status:** not started. Correctly deferred — the roadmap itself flagged this
as "most likely to be deferred" and lowest-ROI of the dealbreakers.
**Est:** 1-2 weeks
**Deps:** none (architecture rework)
@@ -495,6 +539,12 @@ better but doesn't change what maven *is*.
### 4.1 Routing quality (dev embedder)
**Status:** done (`b7eb53a`, 2026-07-06). `make download-embedder` fetches
Xenova/paraphrase-multilingual-MiniLM-L12-v2 (~90MB ONNX) + tokenizer.
AGENTS.md documents embedder + libonnxruntime setup. `queryMinScore` is now
configurable (`voice.query_min_score`, default 0.55) instead of a hardcoded
const.
**Est:** 2-4 h
**Deps:** none
@@ -528,6 +578,11 @@ correctly, not to "clarify"). `make test` green.
### 4.2 Act surface broadening
**Status:** not a code item — operator config. The seeded homelab set
(status/ps/uptime/df/free/logs read-only, restart/stop/reboot gated) ships
in `deploy/mavend.json`. Broadening to home-automation/media/comms is
editing JSON, not code.
**Est:** ongoing config
**Deps:** none
@@ -550,6 +605,10 @@ after adding the tool to `mavend.json` and the act seed file.
### 4.3 LTM ANN (approximate nearest neighbor)
**Status:** deferred (correctly). The `memory.Store` interface is the swap
point; brute-force cosine is sub-ms at single-user scale. Not started until
note+fact count exceeds ~10k and `Search` latency shows up in profiles.
**Est:** ~1 day
**Deps:** none (the interface is the swap point)
@@ -574,6 +633,10 @@ passes the existing `memory_test.go` suite and shows <1ms latency at
### 4.4 Persona prompt
**Status:** done (`b7eb53a`, 2026-07-06). `Persona` field in `VoiceConfig`,
`llmphraser` prepends to `systemPrompt()` + `querySystemPrompt()`. Empty =
current hardcoded feminine-gendered Russian persona (backward compat).
**Est:** 2-4 h
**Deps:** none
@@ -616,6 +679,10 @@ without recompiling. Empty = current behavior. `make test` green.
### 4.5 Custom TTS voice
**Status:** not started. Mostly operator work (record ~50-100 clips, train a
piper model). The code already supports it — `-model` flag takes any piper
voice file, `VoiceConfig.Tts.Voice` names it.
**Est:** ~1 day + training time
**Deps:** none (piper supports custom voices)
@@ -651,10 +718,10 @@ The code already supports it — it's a model-file swap.
### 5.1 Multi-user (SPEC item 8)
**Status:** `SPEC.md:264-270` fences this explicitly: "DO NOT TOUCH THIS
PHASE." No second user exists. The append-only schema (`schema.sql`)
makes it a migration (add `user_id` columns + backfill to "kami"), not a
rewrite. Speaker attribution needs the second voice to train against.
**Status:** deferred by design. SPEC fences this explicitly (`DO NOT TOUCH
THIS PHASE`). No second user exists. The append-only schema makes it a
migration (add `user_id` columns + backfill), not a rewrite. Speaker
attribution needs the second voice to train against.
**When to revisit:** when a second person is actually in the house and
using maven. Not before.
@@ -668,23 +735,25 @@ exist.
## Summary table
| # | Item | Prio | Est | Type | Deps |
|---|------|------|-----|------|------|
| 1.1 | Kuma API key | P1 | 5m | ops | — |
| 1.2 | Voice bind verify + comment fix | P1 | 30m | ops | — |
| 1.3 | desk_active deploy | P1 | 1h | ops | — |
| 2.1 | Cold-start unlock | P2 | 1d | code | — |
| 3.1 | Always-on listening | P3 | 1-2w | code+hw | hardware decision |
| 3.2 | Conversation depth | P3 | 3-5d | code | — |
| 3.3 | Latency/streaming | P3 | 1-2w | code | — |
| 4.1 | Routing quality (dev embedder) | P4 | 2-4h | code+docs | — |
| 4.2 | Act surface | P4 | ongoing | config | — |
| 4.3 | LTM ANN | P4 | 1d | code | scale problem |
| 4.4 | Persona prompt | P4 | 2-4h | code | — |
| 4.5 | Custom TTS voice | P4 | 1d+train | ops | — |
| 5.1 | Multi-user | P5 | deferred | — | second user |
| # | Item | Prio | Est | Type | Deps | Status |
|---|------|------|-----|------|------|--------|
| 1.1 | Kuma API key | P1 | 5m | ops | — | done `eda434f` |
| 1.2 | Voice bind verify + comment fix | P1 | 30m | ops | — | done `eda434f` |
| 1.3 | desk_active deploy | P1 | 1h | ops | — | not done (operator action on `linux`) |
| 2.1 | Cold-start unlock | P2 | 1d | code | — | code done `b0932a1`+`15fe7bb`, **tests missing** |
| 3.1 | Always-on listening | P3 | 1-2w | code+hw | hardware decision | MVP `e57647c` (VAD only, no wake word) |
| 3.2 | Conversation depth | P3 | 3-5d | code | — | done `05236ad` |
| 3.3 | Latency/streaming | P3 | 1-2w | code | — | not started (deferred) |
| 4.1 | Routing quality (dev embedder) | P4 | 2-4h | code+docs | — | done `b7eb53a` |
| 4.2 | Act surface | P4 | ongoing | config | — | not a code item (config) |
| 4.3 | LTM ANN | P4 | 1d | code | scale problem | deferred (scale) |
| 4.4 | Persona prompt | P4 | 2-4h | code | — | done `b7eb53a` |
| 4.5 | Custom TTS voice | P4 | 1d+train | ops | — | not started (ops) |
| 5.1 | Multi-user | P5 | deferred | — | second user | deferred by design |
**Recommended order:** 1.1 → 1.2 → 1.3 (today, ~2h) → 2.1 (security,
~1d) → 4.1 + 4.4 (quick depth, same day) → 3.2 (conversation, ~3-5d) →
3.1 (always-on, needs hardware pick first) → 3.3 (streaming, lowest
ROI of the dealbreakers) → 4.5 (custom voice, when recording is done).
**Remaining work (in priority order):**
1. **2.1 tests** — write the 3 missing keywrap/locked-mode test cases (~30 min)
2. **1.3 desk_active** — install systemd timer + hypridle on `linux` (~1h, your hands)
3. **3.1 wake word** — swap energy-VAD for silero-vad/openWakeWord ONNX in `vad.go`
4. **3.3 streaming** — lowest ROI, defer until 3.1 is real
5. **4.5 custom voice** — when recording is done