299 lines
8.0 KiB
Markdown
299 lines
8.0 KiB
Markdown
# scripts
|
|
|
|
Shell scripts for interacting with the ollie 9P filesystem.
|
|
All scripts read `OLLIE` (default: `$HOME/mnt/ollie`) for the mount path.
|
|
|
|
`mk scripts` installs them and exposes them via the mounted filesystem,
|
|
so they are available without any `$PATH` changes:
|
|
|
|
```sh
|
|
exec $OLLIE/s/sh # start interactive shell
|
|
$OLLIE/s/ls # list sessions
|
|
$OLLIE/s/kill <id> # kill a session
|
|
$OLLIE/s/bfg "my prompt" # foreground one-shot query; blocks until done
|
|
$OLLIE/s/bbg "my prompt" # background one-shot query; prints session path
|
|
$OLLIE/s/cleanup # remove all idle sessions
|
|
$OLLIE/u/optimize "prompt" # generate and return best optimized prompt
|
|
```
|
|
|
|
Scripts are organized by the filesystem namespace they are hosted under:
|
|
|
|
- `s/` — session management and one-shot query scripts
|
|
- `u/` — utility scripts; compositions of other ollie primitives
|
|
- `x/` — elevation plugins; called by `execute_code` for privileged steps
|
|
|
|
---
|
|
|
|
## s/sh
|
|
|
|
Interactive chat interface for ollie sessions. Resumes the most recent
|
|
session for the current directory by default; creates a new one if none
|
|
exists.
|
|
|
|
```
|
|
s/sh [-new] [-resume] [-session ID] [-cwd DIR] [-backend B] [-model M] [-agent A]
|
|
```
|
|
|
|
**Flags**
|
|
|
|
| Flag | Description |
|
|
|---|---|
|
|
| `-new` | Always create a new session |
|
|
| `-resume` | Resume last session for the cwd; error if none |
|
|
| `-session ID` | Attach to a specific session by ID |
|
|
| `-cwd DIR` | Working directory (default: `pwd`) |
|
|
| `-backend B` | Backend override (e.g. `ollama`, `anthropic`) |
|
|
| `-model M` | Model override |
|
|
| `-agent A` | Agent config name |
|
|
|
|
**Input**
|
|
|
|
At the `>` prompt:
|
|
|
|
| Input | Action |
|
|
|---|---|
|
|
| `<text>` | Submit prompt, stream response |
|
|
| `/q <text>` | Enqueue prompt for later |
|
|
| `/<cmd>` | Send to session ctl (e.g. `/compact`, `/clear`) |
|
|
| `/kill` | Kill the session and exit |
|
|
| Ctrl-C | Interrupt running turn (or exit if idle) |
|
|
|
|
**Examples**
|
|
|
|
```sh
|
|
s/sh # resume or create session for pwd
|
|
s/sh -new -model gpt-4o # fresh session with model override
|
|
s/sh -session 1745123456-abc # attach to a specific session
|
|
```
|
|
|
|
---
|
|
|
|
## s/ls
|
|
|
|
List all active sessions.
|
|
|
|
```
|
|
s/ls
|
|
```
|
|
|
|
---
|
|
|
|
## s/kill
|
|
|
|
Kill a session by ID and remove it.
|
|
|
|
```
|
|
s/kill <id>
|
|
```
|
|
|
|
---
|
|
|
|
## s/bfg
|
|
|
|
Foreground one-shot query. Submits a prompt to a new session, blocks until
|
|
the agent is done, writes the result to stdout, then removes the session.
|
|
Exit code is non-zero on failure. Thin wrapper around `s/b`.
|
|
|
|
```
|
|
s/bfg [flags] [prompt...]
|
|
echo "prompt" | s/bfg [flags]
|
|
```
|
|
|
|
Accepts the same flags as `s/b`.
|
|
|
|
**Examples**
|
|
|
|
```sh
|
|
s/bfg "Summarize this repo in one sentence"
|
|
cat error.log | s/bfg "What is causing this error?"
|
|
s/bfg -output json "List the top 3 risks as JSON"
|
|
s/bfg -parallel 4 -keep "Write a haiku about filesystems"
|
|
s/bfg -backend ollama -model qwen3:8b "Explain this function" < main.go
|
|
```
|
|
|
|
---
|
|
|
|
## s/bbg
|
|
|
|
Background one-shot query. Submits a prompt to a new session and returns
|
|
immediately; prints the `s/{id}` path for each job. Thin wrapper around
|
|
`s/b -bg`.
|
|
|
|
```
|
|
s/bbg [flags] [prompt...]
|
|
echo "prompt" | s/bbg [flags]
|
|
```
|
|
|
|
Accepts the same flags as `s/b`.
|
|
|
|
**Examples**
|
|
|
|
```sh
|
|
path=$(s/bbg "write a limerick about Go")
|
|
until [ "$(cat $path/statewait)" = "idle" ]; do :; done
|
|
tail -c +$(($(cat $path/offset) + 1)) $path/chat
|
|
```
|
|
|
|
---
|
|
|
|
## s/b
|
|
|
|
Core one-shot runner. Submits a prompt to a new session, optionally waits,
|
|
and handles parallel fan-out. `s/bfg` and `s/bbg` are both wrappers around
|
|
this script.
|
|
|
|
```
|
|
s/b [flags] [prompt...]
|
|
echo "prompt" | s/b [flags]
|
|
```
|
|
|
|
**Flags**
|
|
|
|
| Flag | Description |
|
|
|---|---|
|
|
| `-name N` | Base session name; sessions are suffixed `-1`, `-2`, ... |
|
|
| `-cwd DIR` | Working directory (default: `pwd`) |
|
|
| `-agent A` | Agent config name |
|
|
| `-backend B` | Backend override |
|
|
| `-model M` | Model override |
|
|
| `-json` | Append JSON-only instruction to prompt |
|
|
| `-parallel N` | Run the same prompt N times in parallel (default: 1) |
|
|
| `-keep` | Do not remove session(s) after printing result |
|
|
| `-bg` | Submit and exit immediately; prints session path(s); implies `-keep` |
|
|
| `-failfast` | On first failure, cancel remaining parallel jobs and exit |
|
|
|
|
---
|
|
|
|
## s/cleanup
|
|
|
|
Remove all idle sessions.
|
|
|
|
```
|
|
s/cleanup
|
|
```
|
|
|
|
---
|
|
|
|
## u/optimize
|
|
|
|
Generates N candidate optimized prompts, judges them, and returns the best
|
|
one to stdout. Debugging output (progress messages) goes to stderr.
|
|
|
|
```
|
|
u/optimize [flags] [prompt...]
|
|
echo "prompt" | u/optimize [flags]
|
|
```
|
|
|
|
**Flags**
|
|
|
|
| Flag | Description |
|
|
|---|---|
|
|
| `-n N` | Number of candidates to generate (default: 3) |
|
|
| `-cb B` | Candidate generation backend |
|
|
| `-cm M` | Candidate generation model |
|
|
| `-jb B` | Judge backend |
|
|
| `-jm M` | Judge model |
|
|
|
|
**Examples**
|
|
|
|
```sh
|
|
u/optimize "Summarize this document"
|
|
u/optimize -n 5 -cm qwen/qwen3-8b -jm anthropic/claude-opus-4.6 "Write a haiku"
|
|
u/optimize "generate a hello world program. use c++." >[2]/dev/null | s/bfg
|
|
```
|
|
|
|
Outputs to stdout, making it composable with other pipeline stages.
|
|
|
|
---
|
|
|
|
## x/elevate
|
|
|
|
Sandbox escape hatch invoked by `execute_code` when a step is marked `elevated: true`.
|
|
The Landlock sandbox is enforced at the kernel level — restrictions apply regardless of
|
|
user privileges within the sandboxed process. `x/elevate` is a generic client that
|
|
forwards the command to an adapter running outside the sandbox, which executes it and
|
|
returns the result.
|
|
|
|
`x/elevate` knows nothing about the backend. It connects to the socket at
|
|
`OLLIE_ELEVATE_SOCKET`, sends `{cmd, cwd}`, and reads back `{stdout, stderr,
|
|
exit_code}`. The adapter on the other end is backend-specific. Multiple adapters can
|
|
coexist at different socket paths; switching backends is a single env var change.
|
|
|
|
Set `OLLIE_ELEVATE_SOCKET` in `~/.config/ollie/env`. The default is
|
|
`$XDG_RUNTIME_DIR/ollie/elevate.sock` (falling back to
|
|
`/run/user/<uid>/ollie/elevate.sock`), so this only needs to be set when using
|
|
a non-default path:
|
|
|
|
```
|
|
OLLIE_ELEVATE_SOCKET=${XDG_RUNTIME_DIR}/ollie/elevate.sock
|
|
```
|
|
|
|
### Protocol
|
|
|
|
`x/elevate` sends a newline-terminated JSON object and reads a JSON response:
|
|
|
|
```
|
|
→ {"cmd": "<shell command>", "cwd": "<working directory>"}\n
|
|
← {"stdout": "...", "stderr": "...", "exit_code": 0}
|
|
```
|
|
|
|
Any process that listens on a Unix stream socket and speaks this protocol is a valid
|
|
adapter.
|
|
|
|
### x/elevate-adapter-superpowerd
|
|
|
|
The included adapter bridges the ollie elevate protocol to superpowerd, a hypothetical
|
|
external command broker. superpowerd is a daemon running outside any sandbox that
|
|
accepts `ExecuteCommand` requests over its own Unix socket and runs them in an
|
|
unsandboxed context — satisfying the kernel-level constraint.
|
|
|
|
**Start the adapter** (outside the sandbox, once per session):
|
|
|
|
```sh
|
|
superpowers run-session -- python3 $OLLIE/x/elevate-adapter-superpowerd
|
|
```
|
|
|
|
`superpowers run-session` acquires a session token and re-runs the adapter with
|
|
`SUPERPOWERD_SESSION_TOKEN` set. The adapter then:
|
|
|
|
1. Creates the socket at `OLLIE_ELEVATE_SOCKET` and listens for connections
|
|
2. For each request, connects to superpowerd and sends a JSON-RPC `ExecuteCommand`:
|
|
|
|
```json
|
|
{
|
|
"jsonrpc": "2.0",
|
|
"method": "ExecuteCommand",
|
|
"id": 1,
|
|
"params": {
|
|
"auth": {"session_token": "<token>"},
|
|
"command": "<cmd>",
|
|
"working_dir": "<cwd>",
|
|
"approval_timeout": 7200
|
|
}
|
|
}
|
|
```
|
|
|
|
3. Translates the response to the ollie protocol and returns it to `x/elevate`
|
|
4. Cleans up the socket on exit (`SIGTERM`/`SIGINT`)
|
|
|
|
The superpowerd socket is resolved from `SUPERPOWERD_SOCKET`,
|
|
`SUPERPOWERD_SOCKET_DIR/superpowerd.sock`, `$XDG_RUNTIME_DIR/superpowerd/superpowerd.sock`,
|
|
or `/run/user/<uid>/superpowerd/superpowerd.sock`.
|
|
|
|
### Writing your own adapter
|
|
|
|
Any daemon that owns `OLLIE_ELEVATE_SOCKET` and speaks the two-message JSON protocol
|
|
is a valid adapter. The daemon must be started outside landrun; that's the only
|
|
constraint. Use `elevate-adapter-superpowerd` as a template.
|
|
|
|
### Disabling elevation
|
|
|
|
Replace `x/elevate` with a script that exits non-zero. Steps marked `elevated: true`
|
|
will fail rather than escape the sandbox:
|
|
|
|
```sh
|
|
#!/bin/sh
|
|
echo "elevation disabled" >&2
|
|
exit 1
|
|
```
|