marvin-turnstone

Local turnstone deployment as a boco container-VM.

host podman build ──> boco build qcow2 ──> boco boot
                                              │  QEMU/KVM (virtio, user-net)
                        ┌─────────────────────┴───────────────────┐
                        │ VM (Arch)                               │
                        │  /boco/init → start-turnstone.sh (root) │
                        │    ├─ sshd            (ops channel)     │
                        │    └─ setpriv marvin                    │
                        │        └─ turnstone-server :8080  PID 1 │
                        └─────────────────────────────────────────┘
   host :8080 ──hostfwd──> web UI        host :2222 ──> guest sshd :22

Prerequisites

  • podman, qemu-base, virtiofsd, boco

Build

scripts/build.sh

Creates configs/ssh/id_ed25519 (ops keypair, once), builds the podman image, then packs it as boco qcow2 into the boco registry.

Run

scripts/run.sh

This exposes the turnstone console on :8080, and ssh on :2222

LLM backend

Set up configs/turnstone/config.toml with an OpenAI-compatible endpoint.

Shares (virtiofs, survives reboots)

Host path Guest path Purpose
configs/turnstone/ /home/marvin/.config/turnstone turnstone config.toml
data/ /var/lib/turnstone SQLite database
work/ /home/marvin/work agent workspace

Note that virtiofsd runs under podman unshare, which means that files written by the guest-VM will be owned by a subuid-range.

Configuration

Edit configs/turnstone/config.toml (see config.toml.example):

  • [models.<provider>] - LLM provider; api_key must be set.
  • [auth] jwt_secret - required, generate once.
  • [database] path - SQLite on the data/ share.
  • [tools] - workspace_dir surfaced to the model.

Personas

Turnstone offers a few built-in personas (Engineer, Writer, Researcher, Scribe, Manager, Executive), which are seeded by turnstone's migration.

This deployment adds a custom default persona marvin (VM-specific: persistence rules, Gitea remotes, podman) via scripts/persona.py - the prompt text is versioned there and re-applied after a DB reset:

python3 scripts/persona.py            # --db data/turnstone.db default

(Without a console deployment, persona CRUD is a direct SQLite write; with turnstone-console running, use its admin API/Personas tab.)

Skills

Skills are checked in under skills in the SKILL.md format. These are imported into turnstone's DB-backed catalog via scripts/import_skills.py. The script runs inside the VM.

scp -O -i configs/ssh/id_ed25519 -P 2222 -r skills scripts/import_skills.py \
    marvin@localhost:/tmp/
ssh -i configs/ssh/id_ed25519 -p 2222 marvin@localhost \
    /opt/turnstone/bin/python /tmp/import_skills.py --dir /tmp/skills

Idempotent (--update re-imports + appends version rows). Reboot the VM after importing - the running server holds a stale WAL snapshot and won't see new rows until restart.

S
Description
No description provided
Readme
115 KiB
0 Stars 0 Watchers 0 Forks
Languages
Python 49.6%
Shell 33.8%
Dockerfile 16.6%