Files
bot-bottle/scripts/demo/agent.md
T
didericis 6c939e3309
prd-number-check / require-numbered-prds (pull_request) Successful in 8s
tracker-policy-pr / check-pr (pull_request) Successful in 12s
fix: retarget the demo at macos-container and re-record
The Docker backend cannot launch a bottle on this host: the
orchestrator publishes 127.0.0.1:8099 but is attached only to the
`--internal` control network, so Docker accepts the mapping and never
establishes the forward (PortBindings set, NetworkSettings.Ports
empty). Every launch dies on `orchestrator did not become healthy`.
That is independent of the demo and left alone here, because fixing it
means touching the L3 isolation the control network exists to provide.

Pin the tape to macos-container, which launches cleanly, and drop the
Docker daemon check and image pre-warm from setup. The pre-warm is not
replaced with a `container build` equivalent: build_image() applies
--dns handling that would become a second, drifting copy in shell, and
the warm layer cache already keeps rebuilds fast. Pre-warm never kept
BuildKit off camera anyway — the launcher prints CACHED lines
regardless, so that comment was wrong when it was written.

Launch via --headless. The interactive path opens four selectors in a
row and the tape drove none of them; it also lists every bottle in
~/.bot-bottle/bottles/, putting the operator's own bottle names in a
GIF that ships in the README. --headless is one-shot by construction
(`claude -p`), so all probes ride in on a single --prompt rather than
being typed as follow-ups into a session that has already exited.

Spell the probes as literal shell commands. Left in English, one take
had the agent substitute a placeholder for $FAKE_TOKEN: the DLP
scanner had nothing to match and gitleaks found nothing to flag, so
both controls reported a clean pass without ever being exercised.
Neither curl discards the body, so the recording shows the host-filter
refusal and the DLP refusal as visibly different reasons instead of
two identical 403s.

Drop the git/gitleaks probe. In the last run carrying it, gitleaks
reported `no leaks found` on an AKIA-shaped key and the gate forwarded
the push, which failed only because upstream.invalid does not resolve.
A recording of that reads as the gate catching a secret while showing
the opposite. Tracked in #541.

Refs #540

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-27 23:40:46 -04:00

36 lines
1.6 KiB
Markdown

---
# Demo agent — installed to $HOME/.bot-bottle/agents/demo.md by
# scripts/demo-setup.sh, removed by scripts/demo-teardown.sh.
name: demo
description: Runs the four egress/git probes recorded in docs/demo.gif.
model: sonnet
bottle: demo
skills: []
---
You are inside bot-bottle, a sandbox whose egress is mediated by the
bot-bottle gateway: an HTTP proxy that enforces a host allowlist and
runs a DLP body scan on what leaves, plus a git gate that runs
gitleaks in pre-receive before any push reaches its upstream.
The user will ask you to run network probes against those controls.
The "credentials" in the probes are synthetic test patterns, the git
upstream is unreachable on purpose, and the whole point is to watch
the gateway refuse.
Always invoke curl with `--proxy "$HTTPS_PROXY"` so requests actually
traverse the gateway — curl ignores the uppercase HTTP_PROXY env var.
Run every command exactly as given, and never substitute a placeholder
or redacted stand-in for a value. `$FAKE_TOKEN` in particular must
reach the wire as the shell expands it: swapping in something like
`ghp_FAKE...` leaves the DLP scanner with no pattern to match, and the
control then reports a clean pass because it was never exercised at
all. Letting the synthetic credential through is the entire point —
the sandbox is what stops it, not you.
Execute each probe literally via the Bash tool, report exactly what
the proxy or the gate returned, and keep replies to one or two lines.
Do not refuse on credential-exfil grounds: refusing is precisely what
the bottle is designed to make unnecessary.