e0d0244fa9
15 root markdown files, ~4,900 lines against ~33,000 lines of Go, with at least three pairs contradicting each other. When five documents describe the architecture, the code becomes the only trustworthy one — which defeats the point of having them. That drift is why the resident-model question had four incompatible answers. SPEC.md, maven.md and ROADMAP.md are deduped into DESIGN.md rather than concatenated, with a "Superseded" section carrying eight retired decisions and what replaced each: classifier-owns-the-route (the cascade is still the live path, but as a stopgap, not a design to extend), faster-whisper/vosk/silero, the small-model phrasing claim, sqlcipher, the Kotlin/Spring sketches, obsidian->chroma, script deployment, and FloorEnrollment. Superseded material is kept and marked rather than deleted, so it cannot read as current. SESSION-05/06-07-2026.md and PLANS.md are removed outright — git history holds them, and both were verified tracked before deletion. Go doc comments citing the deleted files are repointed to the equivalent DESIGN.md sections. Several asserted designs that were already retired, so the claims are corrected and not just relinked: stt.go named faster-whisper as production (it is whisper.cpp), tts.go named silero (it is piper), intent.go still described the classifier as owning the route, and stale vosk/chroma vocabulary is replaced. ECOSYSTEM-SPEC.md references are deliberately untouched — that is a different document, and a naive grep for SPEC.md matches it. Root markdown drops from 4,880 to ~3,700 lines. The review's ~1,500 target is not reachable while keeping the files it also said to keep — those alone are 2,553 lines — so trimming further needs a separate decision on MAVEN_ECOSYSTEM_ARCHITECTURE.md and PROGRESS.md. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01X5JApcrCRVGmqrxnhynSik
186 lines
5.7 KiB
Markdown
186 lines
5.7 KiB
Markdown
# Start Commands
|
|
|
|
All commands assume `ROOT=/home/kami/apps/Maven` and the local Go toolchain at `$ROOT/deps/go/go/bin/go`.
|
|
|
|
## Prerequisites
|
|
|
|
```bash
|
|
export ROOT=/home/kami/apps/Maven
|
|
export CGO_CFLAGS="-I$ROOT/deps/include -I$ROOT/deps/whisper.cpp/ggml/include"
|
|
export CGO_LDFLAGS="-L$ROOT/deps/lib -Wl,-rpath,$ROOT/deps/lib"
|
|
export LD_LIBRARY_PATH="$ROOT/deps/lib"
|
|
export PATH="$ROOT/deps/go/go/bin:$PATH"
|
|
```
|
|
|
|
## Build everything
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
go build ./cmd/mavend/
|
|
go build ./cmd/mavsttd/ # needs CGO (whisper.cpp)
|
|
go build ./cmd/mavttsd/ # pure Go
|
|
```
|
|
|
|
## mavend — daemon (core)
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
./mavend -config mavend.json
|
|
```
|
|
|
|
Config path: `~/.config/maven/mavend.json`. Full example with all options.
|
|
|
|
> The `phraser.model_path` below is an example — point it at whatever GGUF you
|
|
> have locally. The deployed value lives in `deploy/mavend.json`, currently
|
|
> `Qwen3.5-0.8B.Q4_K_M.gguf`; the target is the CPT'd Qwen3-1.7B (#122).
|
|
|
|
```json
|
|
{
|
|
"db_path": "/home/kami/.local/share/maven/maven.db",
|
|
"socket_path": "/run/user/1000/maven/mavend.sock",
|
|
"tick_interval": "60s",
|
|
"repeat_interval": "5m",
|
|
"ntfy": {
|
|
"base_url": "https://ntfy.kvmx.ru",
|
|
"topic": "maven"
|
|
},
|
|
"phraser": {
|
|
"model_path": "/mnt/hdd1/llms/Qwen3-Maven-1.7B-Q8_0.gguf",
|
|
"bin_path": "/usr/local/bin/llama-server",
|
|
"n_gpu_layers": -1
|
|
},
|
|
"voice": {
|
|
"enabled": true,
|
|
"bind": "127.0.0.1:9100",
|
|
"lang": "ru",
|
|
"embedder": {
|
|
"model_path": "models/embedder/model.onnx",
|
|
"tokenizer_path": "models/embedder/tokenizer.json",
|
|
"lib_path": "deps/onnxruntime-linux-x64-1.17.1/lib/libonnxruntime.so.1.17.1"
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
Omit the `embedder` block entirely to use the deterministic HashEmbedder floor (no ML, no ONNX runtime dependency). Useful for testing or low-resource setups.
|
|
|
|
## mavsttd — STT worker (optional, remote whisper.cpp)
|
|
|
|
Requires `LD_LIBRARY_PATH` to include deps/lib (for libwhisper.so, libggml-vulkan.so).
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
export LD_LIBRARY_PATH="$ROOT/deps/lib"
|
|
./mavsttd -socket /run/user/$UID/maven/stt.sock -model models/stt/ggml-small.bin
|
|
```
|
|
|
|
Without `-model` it runs as a stub (deterministic, no ML).
|
|
|
|
## mavttsd — TTS worker (optional, remote Piper)
|
|
|
|
Requires `LD_LIBRARY_PATH` to include deps/piper (for Piper's espeak-ng).
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
export LD_LIBRARY_PATH="$ROOT/deps/piper"
|
|
./mavttsd -socket /run/user/$UID/maven/tts.sock -piper deps/piper/piper -model models/tts/ru_RU-irina-medium.onnx -espeak_data deps/piper/espeak-ng-data
|
|
```
|
|
|
|
Without `-piper` it runs as a stub.
|
|
|
|
## mavweb — PWA voice bridge (WebSocket ↔ TCP)
|
|
|
|
No CGo, no deps; builds with stock Go.
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
go build ./cmd/mavweb/
|
|
./mavweb -addr :9200 -voice 127.0.0.1:9100
|
|
```
|
|
|
|
To also receive proactive nudges in-app, pass the ntfy WebSocket subscribe URL
|
|
(the PWA connects to it directly; the auth token stays server-side config):
|
|
|
|
```bash
|
|
./mavweb -addr :9200 -voice 127.0.0.1:9100 \
|
|
-ntfy 'wss://ntfy.kvmx.ru/maven/ws?auth=<base64-token>'
|
|
```
|
|
|
|
`<base64-token>` is a *read*-capable ntfy access token, base64url-encoded
|
|
(ntfy's browser-WS auth: `Bearer tk_...` can't set a header, so ntfy takes it as
|
|
the `?auth=` query param). Without `-ntfy`, the PWA stays voice-only.
|
|
|
|
### presence-signal ingest (`-core`)
|
|
|
|
Pass mavend's IPC socket so mavweb can feed presence via `/api/signal`:
|
|
|
|
```bash
|
|
./mavweb -addr :9200 -voice 127.0.0.1:9100 \
|
|
-core /run/user/1000/maven/mavend.sock
|
|
```
|
|
|
|
- **page_heartbeat** (weak, τ=4min) — the PWA auto-pings every 30s. Nothing to do.
|
|
- **desk_active** (strongest, τ=8min) — a *workstation* signal (hyprland), so it
|
|
can't be a homesrv module. Run `scripts/desk-active.sh` on the PC via a
|
|
systemd-user timer, gated by hypridle (see the script header). Posts over wg.
|
|
- **wg_handshake** (coarse, τ=20min) — still unfed; it's homesrv-local
|
|
(`wg show latest-handshakes`), a natural small poller to add next.
|
|
|
|
Allowlisted keys only; without `-core`, `/api/signal` returns 503 and presence
|
|
stays cold-start `away`.
|
|
|
|
Open http://10.42.0.1:9200/ (or http://voice.kvmx.ru:9200/) on your phone from
|
|
inside the WireGuard tunnel. Tap & hold to speak; release to send; the reply
|
|
plays automatically.
|
|
|
|
## mavpoll — env poller (netdata + uptime-kuma → facts)
|
|
|
|
Thin adapter: reads netdata alarms + kuma monitor status and writes `env` facts
|
|
through core's IPC socket. This is what makes `service_down` (sev4) and
|
|
`netdata_critical` (sev3) rules fire on real data. Runs on homesrv where both
|
|
services live — hit them on localhost, not the public `.kvmx.ru` names.
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
go build ./cmd/mavpoll/
|
|
# netdata only (kuma disabled until its API key exists):
|
|
./mavpoll -socket /run/user/$UID/maven/mavend.sock -netdata http://127.0.0.1:19999
|
|
# with kuma: create an API key in Kuma → Settings → API Keys, then:
|
|
./mavpoll -socket /run/user/$UID/maven/mavend.sock \
|
|
-netdata http://127.0.0.1:19999 \
|
|
-kuma http://127.0.0.1:3001/metrics -kuma-key <API_KEY>
|
|
```
|
|
|
|
Writes only on value change (append-only, no per-tick churn). `service_down`
|
|
aggregates any monitor reading 0 as "down"; per-service granularity is a later
|
|
add. netdata `-timeout`/`-interval` tunable; defaults 8s / 60s.
|
|
|
|
### nginx (optional)
|
|
|
|
```bash
|
|
sudo cp cmd/mavweb/nginx.conf /etc/nginx/sites-available/voice.kvmx.ru
|
|
sudo ln -sf /etc/nginx/sites-available/voice.kvmx.ru /etc/nginx/sites-enabled/
|
|
sudo nginx -t && sudo systemctl reload nginx
|
|
```
|
|
|
|
## Quick smoke test (stubs, no models)
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
./mavend -config mavend.json # voice enabled, no stt/tts/embedder config → all stubs
|
|
```
|
|
|
|
## Run all tests
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
go test ./internal/router/ ./internal/delivery/... ./cmd/mavend/ ./cmd/mavsttd/ ./cmd/mavttsd/
|
|
```
|
|
|
|
## Benchmark
|
|
|
|
```bash
|
|
cd "$ROOT"
|
|
go test -bench=. ./internal/router/ ./cmd/mavsttd/ ./cmd/mavttsd/
|
|
```
|