# Larry-Anywhere Portable AI agent for Cloverleaf integration work. Single bash script, no installs, no root, no package manager. Runs on Linux and inside MobaXterm on Windows. **26 native v3 tools** for NetConfig analysis, message search, system documentation, regression testing, and safe NetConfig modification — all implemented directly in bash with no dependency on v1 wrapper scripts or v2 `cloverleaf-tools.pyz`. When Cloverleaf is installed, Larry uses the shipped product binaries (`tclsh`, `hcienginerun`, etc.) directly. Otherwise it falls back to bash one-liners it composes itself. Never relies on the v1/v2 wrapper layers. ## Install ### One-liner (recommended) On any client box with `curl` and `bash` (essentially any Linux + MobaXterm shell): ```bash curl -fsSL https://raw.githubusercontent.com/bojj27/cloverleaf-larry/main/install-larry.sh | bash ``` The installer: - Detects platform (Linux / Darwin / MobaXterm-cygwin) and arch - Creates `~/.larry/` (or wherever `$LARRY_HOME` points) - Pulls every script + agent file from `bojj27/cloverleaf-larry` raw URLs - Downloads a static `jq` binary into `~/.larry/bin/` if `jq` isn't on PATH - Drops a `larry` shim into `~/bin/` - Makes no system changes, requires no root First run: ```bash larry # prompts for ANTHROPIC_API_KEY once # saved to ~/.larry/.env mode 0600 ``` ### Auto-update Every time you run `larry`, it self-updates from the canonical GitHub URL. To suppress for one launch: `larry --no-update`. To disable permanently: `export LARRY_NO_UPDATE=1`. ### Uninstall (remove everything the installer put down) ```bash larry uninstall # DRY-RUN: lists exactly what would be removed larry uninstall --yes # actually delete (or run uninstall-larry.sh directly) larry uninstall --keep-data # remove program files, keep sessions/journal/creds ``` Reverses `install-larry.sh` exactly: removes `$LARRY_HOME` (the whole install dir, the bundled `jq` fallback, the optional Presidio `phi-venv`, and all runtime artifacts incl. `log/headers.log`, sessions, journal, lessons, knowledge, sanitize, and the `.api-key`/`.env`/`.oauth.json`/`.ssh-*` credential files) **and** the `larry` shim at `$LARRY_BIN_DIR/larry` (default `~/bin/larry`). It stops a running PHI sidecar / tunnel first (via their own pidfiles). It removes **only** what the installer created — it never touches your shell rc, your Cloverleaf sites, or `$HCIROOT`. If you added a `PATH` export by hand, it reminds you to remove that one line. ### Deterministic-only mode (`--no-api`, zero LLM cost) ```bash larry --no-api # interactive REPL with the model rail OFF (env: LARRY_NO_API=1) ``` Makes **zero** LLM API calls. The REPL and every deterministic command still work; a free-text prompt is answered by pointing you at the matching `larry tools ` command (the same `nc-*` / `hl7-*` tools the model would have invoked) instead of calling the model. No API key is required in this mode. Open-ended reasoning / free-form authoring are unavailable and say so clearly. (See also `larry tools list` for the standalone, no-REPL toolkit.) ### Offline / scp install (when the client box can't reach github.com) ```bash # from a machine that CAN reach github git clone https://github.com/bojj27/cloverleaf-larry scp -r cloverleaf-larry/ user@client-box:~/cloverleaf-larry/ ssh user@client-box cd ~/cloverleaf-larry && ./install-larry.sh ``` The installer detects local files and uses them when `LARRY_BASE_URL` isn't reachable. ## Use Set the Cloverleaf runtime context, then point Larry at your site: ```bash export HCIROOT=/opt/cloverleaf/cis2025/integrator export HCISITE=adt larry "$HCIROOT/$HCISITE" you> list every protocol in this site you> find threads with codametrix in the name you> show messages from to_3m in the last 3 days for MRN 5720501458 you> generate jump threads for every TCP-listener inbound, target host=newlinux01.test, jump port = orig+10000 you> diff the ADTto_3m interface + connected threads between test and prod you> document the codametrix system into ~/.larry/knowledge/codametrix.md you> /quit ``` ### What Larry can do natively (v3 tools) | domain | tools | |---|---| | File system | `read_file`, `list_dir`, `grep_files`, `glob_files`, `write_file`, `bash_exec` | | NetConfig (read) | `nc_list_protocols`, `nc_list_processes`, `nc_protocol_block`, `nc_protocol_field`, `nc_protocol_nested`, `nc_protocol_summary`, `nc_destinations`, `nc_sources`, `nc_xlate_refs`, `nc_tclproc_refs` | | NetConfig (write, journaled) | `nc_insert_protocol`, `nc_add_route` | | Workflows | `nc_find_inbound`, `nc_make_jump`, `nc_document`, `nc_find`, `nc_diff_interface` | | Messages (smat is SQLite!) | `hl7_field`, `nc_msgs`, `hl7_diff` | | Safety | `larry_rollback_list` + `larry-rollback.sh` CLI | Every write goes through a journal (`~/.larry/journal//`) — original snapshotted, diff saved, atomic replacement. Roll back any subset with `larry-rollback.sh --list`, `--target /path/to/file`, `--session `, or `--entry `. ### Slash commands in the REPL | command | what | |---|---| | `/env` | show detected HCIROOT/HCISITE + tool layer presence | | `/sites` | list site dirs under HCIROOT | | `/site ` | switch HCISITE mid-session | | `/cd ` | change working directory | | `/model ` | switch Claude model | | `/reset` | clear conversation history | | `/load ` | load a file as your next message | | `/help` | full slash-command help | ## Working examples (battle-tested against a 22-site Cloverleaf install) 1. **Migration jump-threads**: "find every TCP-listener inbound, generate the 3-thread jump pair (linux__out / windows__in / windows__out) for each." Inserts via journaled write. Roll back instantly. 2. **MRN search**: "messages from to_3m in last 3 days for patient MRN X." Reads smat via `sqlite3 -ascii`, parses HL7 natively, filters by PID field — no Cloverleaf binary involved. 3. **System documentation**: "find all threads matching , document them." Cross-site walk, threads + ports + processes + xlates + tclprocs, adjacent-thread map, placeholder POC/status/escalation sections. 4. **Interface diff**: "diff ADTto_3m + connected (depth 1) between test and prod." Connected-graph BFS, protocol-block diff + xlate-file diff + tclproc-file diff. 5. **Regression diff (Phase 6)**: `hl7_diff` for any two HL7 message files, with `--ignore MSH.7` by default and configurable field-level exceptions. The orchestrator that drives Cloverleaf's `route_test` end-to-end is the only Example 6 piece pending an engine to invoke against. ## Architecture in one diagram ``` Agent layer Larry-Anywhere (this repo) ├── bash REPL → Anthropic API ├── personas: Larry + Clover + Regress + Cheatsheet ├── 26 native tools (no v1/v2 deps) └── journal-backed writes with rollback │ ↓ acts on Cloverleaf install $HCIROOT / $HCISITE NetConfig, Xlate/, tables/, tclprocs/, formats/ .smatdb files (SQLite!) under exec/processes/ shipped binaries (tclsh, hcienginerun, ...) — invoked directly via bash_exec when needed for engine ops ``` No layer between Larry and Cloverleaf except plain bash. The v1 wrapper scripts (`tbn`, `hlq`, `mr`, `mp`, `mg`, `awkcut`, ...) and the v2 `cloverleaf-tools.pyz` are intentionally absent. ## Environment cheat-sheet | var | default | purpose | |---|---|---| | `LARRY_HOME` | `~/.larry` | where state lives (sessions, journal, .env, agent overrides) | | `LARRY_MODEL` | `claude-sonnet-4-6` | Claude model (try `claude-opus-4-7` for deeper work) | | `LARRY_MAX_TOKENS` | `8192` | per-turn output cap | | `LARRY_NO_UPDATE` | `0` | set to `1` to disable self-update | | `LARRY_UPDATE_URL` | github.com/bojj27/cloverleaf-larry/main/larry.sh | self-update source | | `LARRY_AGENTS_URL` | github.com/bojj27/cloverleaf-larry/main/agents | persona refresh source | | `ANTHROPIC_API_KEY` | (prompted on first run) | API key, saved to `$LARRY_HOME/.env` | | `HCIROOT` / `HCISITE` | (unset) | auto-detected and surfaced in system prompt | ## Roll back any change Larry made ```bash larry-rollback.sh --list # see every write Larry made, newest first larry-rollback.sh --target /opt/cloverleaf/.../NetConfig # undo every change to this file larry-rollback.sh --session 2026-05-26-090724-12345 # undo a whole Larry session larry-rollback.sh --last 1 # undo the most recent write larry-rollback.sh --entry / # undo one specific write ``` Pre-rollback copies are left at `.larry-prerollback.` so you can re-do if needed. ## Hard limits (V3) - **No subagent dispatch** — Larry + Clover + Regress live in one head. No Pax / Iris / Vera / etc. in portable mode. - **No memory layer** — Honcho / Hindsight / mem0 aren't reachable from a remote client box yet. Session history is the markdown logs in `$LARRY_HOME/sessions/`. - **`read_file` capped at 250 KB**, `grep_files`/`glob_files` 300 results, `bash_exec` 500 lines of output. Use targeted queries. - **Subscription OAuth not yet wired** — API key path only. Claude.ai Max subscription quota uses a different auth flow (OAuth device-code); landing in a future release. ## Reverse SSH tunnel back home (optional) If you also want your home Larry to dial into the client shell: ```bash ~/.larry/larry-tunnel.sh --serveo # zero-config (serveo.net, third-party) ~/.larry/larry-tunnel.sh --hop=user@bjnoela.com:22 # your controlled hop ``` Auto-reconnect built in. PID and public URL written to `~/.larry/tunnel.{pid,url}`. ## License GPL? MIT? TBD. Bryan decides before this repo gets shared widely. ## Issues / PRs [github.com/bojj27/cloverleaf-larry](https://github.com/bojj27/cloverleaf-larry)