Expand the documentation with measured figures and operational detail
Most of this replaces "roughly 550 characters per tool" with the actual per-tool measurements, and fills in the parts a reader hits after the happy path: what a specific error means, what a setting costs, what is not covered. Measured rather than estimated: - Per-tool byte cost, all fourteen, and the per-set totals. 7,673 B for the full set, averaging 548. - Builtin skill bodies at 5,284 B against a 681 B catalogue, which is the argument for loading bodies on demand. - Full system prompt 3,571 chars, core-only 2,045. New sections: - tools: which sets to keep and why, the jail function itself, an output-cap table, and the real error strings for edit_file and multi_edit. - configuration: env var per provider preset, cost-estimate limits, what each --no-* flag isolates, and three settings that do more than they look like. - agents: step caps per variant, which variant to reach for, and the fact that reasoning is charged as output and discarded first by compaction. - headless: exit code 0 means "the turn completed", not "the answer was yes" — with the jq pattern for gating on content. Timeouts, concurrent -c runs fighting over one session, CI recipes for --no-skills. - mcp: parallel connect, startup cost, a debugging ladder, and that toolSets does not gate MCP tools. - registry: publishing, local testing over http://localhost, and a troubleshooting section keyed on the actual validator messages. - memory: what compaction discards in what order, /compact versus automatic pruning, and that -c matches on cwd. - skills: the frontmatter reader's limits, and how to verify a skill loaded. Corrections found while cross-checking against the source: - The guard table was missing --force-with-lease and > /dev/sd… - The done event's token fields are optional, so the jq example filters on one rather than assuming it. Two honest limits now written down: the guard matches command strings, so a base64-decoded or script-wrapped command is not caught; and a registry index is trusted for its contents, not its authorship. Verified: all internal links and heading anchors resolve, every docs/ page is reachable from the README, 538 tests pass, typecheck clean.
This commit is contained in:
@@ -74,6 +74,29 @@ told and can respond to it.
|
||||
if shiro -p "does this build?" --yolo; then echo ok; else echo failed; fi
|
||||
```
|
||||
|
||||
That distinction is deliberate and it has a consequence: **a successful run says nothing about
|
||||
whether the answer was yes.** `0` means the turn completed, not that the build passed. To gate CI
|
||||
on the content, read the output:
|
||||
|
||||
```bash
|
||||
shiro -p "Does this build? Answer only YES or NO." --json --yolo \
|
||||
| jq -r 'select(.type=="text") | .text' | grep -q YES
|
||||
```
|
||||
|
||||
Anything that must fail the build has to be asserted on text or, better, on the exit code of a
|
||||
real command the agent ran.
|
||||
|
||||
## Timeouts
|
||||
|
||||
There is no wall-clock limit on a headless run. Three things bound it:
|
||||
|
||||
- `maxSteps` per variant — 12 for `quick`, 50 by default, 80 for `deep`.
|
||||
- The `timeout` the model passes to `bash`, 120 s by default and 600 s at most.
|
||||
- Whatever your CI runner enforces, which is the only hard stop.
|
||||
|
||||
Interactively `ctrl-c` kills one command and keeps the turn. Headless has no terminal for that, so
|
||||
a signal ends the run. In CI, prefer `--agent quick` and a runner timeout over hoping.
|
||||
|
||||
## Sessions
|
||||
|
||||
Headless runs save like interactive ones, so `-c` picks up where one left off:
|
||||
@@ -83,6 +106,14 @@ shiro -p "start the refactor" --yolo
|
||||
shiro -p "now update the tests" --yolo -c
|
||||
```
|
||||
|
||||
Useful, and worth knowing the shape of: each `-p` run is **one turn**, and `-c` resumes the newest
|
||||
session for that directory. Two concurrent runs in the same directory therefore fight over the
|
||||
same session, and the second overwrites the first. Pass `-r <id>` to keep parallel runs separate,
|
||||
or point them at different `SHIRO_HOME` directories.
|
||||
|
||||
Memory also accumulates. An unattended loop calling `remember` writes to the project store like
|
||||
any other run, so `--no-memory` is worth considering for a job that runs on every push.
|
||||
|
||||
## What is withheld
|
||||
|
||||
The `ask` tool is not offered at all, rather than being offered and left to hang. The model
|
||||
@@ -131,8 +162,34 @@ env:
|
||||
OPENAI_API_KEY: ${{ secrets.OPENAI_API_KEY }}
|
||||
```
|
||||
|
||||
Two more worth having in a workflow. Trim the tool schema to what the job needs, since a CI run
|
||||
pays for it on every step:
|
||||
|
||||
```yaml
|
||||
- run: echo '{ "toolSets": [] }' > ~/.shiro-neko/config.json
|
||||
```
|
||||
|
||||
And keep an unattended job from inheriting an installed skill nobody reviewed:
|
||||
|
||||
```yaml
|
||||
- run: shiro -p "..." --agent review --no-skills --no-plugins
|
||||
```
|
||||
|
||||
`--no-skills` matters more in CI than locally: a skill installed from a registry is instructions
|
||||
in the system prompt, and CI is exactly where nobody is watching what it says. See
|
||||
[registry](registry.md).
|
||||
|
||||
## Cost control
|
||||
|
||||
Headless runs are unattended, so a runaway loop costs real money. `--agent quick` caps the
|
||||
step count at 12, and `{ "toolSets": [] }` trims the schema sent every request. There is no
|
||||
spend ceiling yet — see [TODO.md](../TODO.md).
|
||||
|
||||
What a run actually costs is in the `done` event, so a wrapper can total it:
|
||||
|
||||
```bash
|
||||
shiro -p "..." --json --yolo | jq -r 'select(.type=="done" and .inputTokens) | "\(.inputTokens) in, \(.outputTokens) out"'
|
||||
```
|
||||
|
||||
The token fields are optional: an aborted turn emits `done` with neither, which is why the filter
|
||||
checks for one rather than assuming it.
|
||||
|
||||
Reference in New Issue
Block a user