Mark Phase 3 (Spark Control) done; trim spec to live command contract
Shipped in Spark Control v0.21.0: status badge + Update/Restart/Stop-Start/Logs
tile. All three exit criteria confirmed. matrix-bridge needed no code change.
- AGENTS.md: Current state + ROADMAP Phase 3 -> DONE; Deploy switched scp -> git
pull (Update button); D10 stamped; new Infra fact for the Spark->Gitea path and
the load-bearing IdentitiesOnly ssh-config pin the Update button depends on.
- spark-control-integration.md: trimmed from dev spec to live contract (dropped
sudo -iu fallback and dev-side scaffolding; folded in direct-as-modelo, the
Gitea key gotcha, restart cadence, and the LAN-only HTTP API).
- README: dropped stale "pre-Phase 0" status; Setup reframed for a fresh install.
Deferred follow-up: badge reflects container liveness only, not Matrix
connectivity; HEALTHCHECK + {{.State.Health.Status}} is the matrix-bridge-side fix.
This commit is contained in:
@@ -61,20 +61,23 @@ the full answer back into the room (ask mode, D12).
|
||||
- **Bot — venv (dev/fallback):** `python3 -m venv .venv && .venv/bin/pip install -r requirements.txt`,
|
||||
then `.venv/bin/python src/bot.py` — uses modelo's host `~/.ssh/config` for the alias.
|
||||
`MB_SSH_ALIAS` overrides the SSH target for testing.
|
||||
- **Deploy:** pull the bot files from the Mac (no Gitea needed) —
|
||||
- **Deploy:** the Spark's `~/matrix-bridge` is a Gitea clone tracking `master`, so deploy =
|
||||
`git fetch origin && git reset --hard origin/master && docker compose up -d --build` (run as
|
||||
`modelo` from `~/matrix-bridge`). You normally don't run this by hand — the **Update** button on
|
||||
the Spark Control dashboard (Phase 3) runs exactly this and streams the output: push to Gitea,
|
||||
then click Update. *(Fallback if Gitea is ever unreachable: scp the files from the Mac —
|
||||
`scp mac-bridge:/Users/macpro/Projects/matrix-bridge/{Dockerfile,docker-compose.yml,docker-entrypoint.sh,requirements.txt,config.toml,.env} .`
|
||||
and `scp -r mac-bridge:/Users/macpro/Projects/matrix-bridge/src .`, then rebuild.
|
||||
*(Phase 3 switches this to `git pull` once the Spark's `~/matrix-bridge` becomes a Gitea clone —
|
||||
see `docs/spark-control-integration.md`; not done yet, so scp-from-Mac is still the live path.)*
|
||||
and `scp -r mac-bridge:/Users/macpro/Projects/matrix-bridge/src .`, then rebuild.)*
|
||||
|
||||
## Layout
|
||||
|
||||
- `AGENTS.md` — this file (canonical; `CLAUDE.md` is a relative symlink to it).
|
||||
- `ROADMAP.md` — Phases 1–4+ with falsifiable exits, plus deferred/future directions.
|
||||
- `README.md` — human-facing intro.
|
||||
- `docs/spark-control-integration.md` — Phase 3 spec for the Spark Control dev: the SSH
|
||||
command contract (status / restart / git-pull update) the dashboard drives, plus the one-time
|
||||
conversion of the Spark's `~/matrix-bridge` to a Gitea clone. matrix-bridge needs no code change.
|
||||
- `docs/spark-control-integration.md` — the live Phase 3 command contract: the SSH commands
|
||||
(status / restart / git-pull update / logs) behind the Spark Control tile, plus the now-done
|
||||
one-time conversion of the Spark's `~/matrix-bridge` to a Gitea clone. matrix-bridge needs no
|
||||
code change. (Shipped in Spark Control v0.21.0; see Current state.)
|
||||
- `scripts/launch-claude.sh` — the Mac-side launch wrapper (the only seam that knows the
|
||||
Mac's environment).
|
||||
- `config.example.toml` — room→repo mapping template; the real `config.toml` is gitignored.
|
||||
@@ -125,8 +128,11 @@ Condensed from the scoping workshop. Each: the call, why, what it beat.
|
||||
- **D9 — E2EE deferred (documented tradeoff).** Single-user bot over WireGuard on a private
|
||||
LAN; transport is already private and matrix-nio E2EE adds libolm overhead. *Revisit when:*
|
||||
the bot ever handles sensitive content over untrusted transport.
|
||||
- **D10 — Spark Control manages the bot (Phase 3).** Status on the dashboard + one-click
|
||||
update/restart, the same SSH-behind-buttons pattern Spark Control uses for the Sparks today.
|
||||
- **D10 — Spark Control manages the bot (Phase 3, DONE 2026-06-16).** Status badge + Update /
|
||||
Restart / Stop-Start / Logs buttons on the dashboard, the same SSH-behind-buttons pattern Spark
|
||||
Control uses for the Sparks. Shipped in Spark Control v0.21.0; connects directly as `modelo` (no
|
||||
`sudo` wrap — this Spark has no passwordless sudo, so the spec's different-user branch never
|
||||
applies). Badge reflects container liveness, not Matrix connectivity (see Current state / spec).
|
||||
- **D11 — Launch into a desktop Terminal, not a headless token (Phase 0).** The SSH session
|
||||
can't reach the GUI login Keychain, so a plain `ssh … claude` reports "Not logged in." Rather
|
||||
than mint a long-lived `claude setup-token`, the launcher (`scripts/gui-launch.sh`) uses
|
||||
@@ -176,6 +182,11 @@ once" is not done.
|
||||
- **Spark → Mac:** SSH alias `mac-bridge` → the Mac as user `macpro`, dedicated key
|
||||
(`~/.ssh/id_ed25519` on the Spark, in the Mac's `authorized_keys`). The Spark host's `~/.ssh/config` needs `IdentitiesOnly yes` because a
|
||||
`Host *` rule shadows the default key; the container regenerates a clean config from `config.toml [mac]`.
|
||||
- **Spark → Gitea (deploy/update path):** `~/matrix-bridge` is a git clone tracking `origin/master`
|
||||
(`ssh://git@immense-voyage.local:59916/grant/matrix-bridge.git`). modelo's `~/.ssh/config` pins the
|
||||
deploy key for the Gitea host with `IdentitiesOnly yes` — without it git offered the wrong key first
|
||||
and Gitea returned `Permission denied (publickey)`. **The Spark Control Update button depends on that
|
||||
ssh-config block; flag it if modelo's account is ever rebuilt.**
|
||||
- **Mac → Spark:** no authorized key — direct Mac-initiated Spark ops stay owner-run. (This is *not*
|
||||
what Phase 3 closes: Spark Control already has its own SSH channel into `spark-32d0`, so its
|
||||
status/update/restart buttons ride that, not a Mac→Spark key.)
|
||||
@@ -191,18 +202,33 @@ once" is not done.
|
||||
|
||||
## Current state
|
||||
|
||||
- **Live on the Spark (Phases 0–2 + ask mode).** matrix-nio bot in a Docker container
|
||||
(`~/matrix-bridge`, `docker compose up -d --build`): host networking, `restart: unless-stopped`,
|
||||
- **Live on the Spark (Phases 0–3 + ask mode).** matrix-nio bot in a Docker container
|
||||
(`~/matrix-bridge`, now a Gitea clone tracking `master`): host networking, `restart: unless-stopped`,
|
||||
read-only mounts of `.env`/`config.toml`/SSH key. Runs as `@agent` in 11 project rooms + an
|
||||
all-projects fan-out room. Both modes proven — interactive (plain msg → phone via Remote Control)
|
||||
and ask (`?`-prefix → full answer posted back; D12).
|
||||
- **Phase 2 — DONE** (owner-confirmed N=3: routes by `room_id`, correct repo, zero wrong-dir launches).
|
||||
- **Phase 3 (Spark Control) — IN PROGRESS, awaiting the Spark Control dev.** The contract is
|
||||
`docs/spark-control-integration.md`: status/restart/git-pull-update SSH commands + a one-time
|
||||
conversion of the Spark's `~/matrix-bridge` to a Gitea clone. matrix-bridge needs no code change;
|
||||
remaining work is Spark Control-side (tile + buttons) + the one-time migration. **When live:** trim
|
||||
the spec to the lean command contract, update the Commands "Deploy" entry (scp → git pull), flip
|
||||
Phase 3 → DONE.
|
||||
- **Open / risks:** a `?`-ask in a repo `claude` has never opened may stall on the folder-trust gate
|
||||
— add a trust flag to `ask-claude.sh` if/when hit, not preemptively.
|
||||
- **Phase 3 (Spark Control) — DONE (2026-06-16), shipped in Spark Control v0.21.0.** matrix-bridge
|
||||
tile under "Always-on services": live status badge + Update / Restart / Stop-Start / View-logs
|
||||
buttons, running exactly the spec's commands (`docker inspect` status, `docker restart`, the
|
||||
`git fetch && git reset --hard origin/master && docker compose up -d --build` update streamed live
|
||||
with a ~25-min ceiling, `docker logs --tail 100`). All three exit criteria confirmed (status visible
|
||||
+ reflects container, update works, restart works). matrix-bridge needed no code change. Deviation:
|
||||
connects **directly as `modelo`** (no `sudo -iu` wrap — no passwordless sudo here, so the spec's
|
||||
different-user branch never applies); tile auto-hides when its SSH-user field is blank or the
|
||||
container is absent. A LAN-only HTTP API also exists if scripting is ever wanted:
|
||||
`POST /api/matrix-bridge/update` (+ `/{id}/stream` SSE), `GET /api/matrix-bridge/logs?tail=N`,
|
||||
status via `GET /api/services`.
|
||||
- **Open / risks:**
|
||||
- **Badge = container liveness only, not Matrix connectivity** — a `running` bot disconnected from
|
||||
Synapse still shows Healthy. Clean fix when "running but silent" bites: a Docker `HEALTHCHECK`
|
||||
(bot-side liveness signal) so the tile can read `{{.State.Health.Status}}` — a matrix-bridge-side
|
||||
change; then ping the Spark Control dev to read the health field.
|
||||
- **Update button depends on modelo's Gitea ssh-config pin** (`IdentitiesOnly yes`, see Infra
|
||||
facts) — flag it if modelo's account is ever rebuilt.
|
||||
- A `?`-ask in a repo `claude` has never opened may stall on the folder-trust gate — add a trust
|
||||
flag to `ask-claude.sh` if/when hit, not preemptively.
|
||||
- Cosmetic: a fast `docker restart` won't visibly flip the badge red (panel re-checks status only
|
||||
after the command returns, container already back up); a full `docker stop` turns it red within
|
||||
~5s. Polling cadence, not a bug.
|
||||
- **Repo:** `master` == `phase-1`, clean, pushed to Gitea. No test suite (pre-existing).
|
||||
|
||||
Reference in New Issue
Block a user