diff options
| author | Igor Soarez <igor@soarez.org> | 2026-11-05 20:22:02 +0200 |
|---|---|---|
| committer | Igor Soarez <igor@soarez.org> | 2026-11-05 20:22:02 +0200 |
| commit | 93cdec89edb819984c475c60dcbad51293339e77 (patch) | |
| tree | 942f6a05654843d62015e968986a2c0ba3d238d9 /tests | |
| parent | 9575ead9c637a2dc482c00f417a1d784d46e076a (diff) | |
name pi sessions automatically, replacing the pi-auto-session-name package
Diffstat (limited to 'tests')
| -rwxr-xr-x | tests/fake-model.py | 13 | ||||
| -rwxr-xr-x | tests/pi-live.sh | 42 |
2 files changed, 51 insertions, 4 deletions
diff --git a/tests/fake-model.py b/tests/fake-model.py index 98a61db..a00ccb2 100755 --- a/tests/fake-model.py +++ b/tests/fake-model.py @@ -2,7 +2,8 @@ """A fake OpenAI-compatible model for tests/pi-live.sh: streams a short reply to /v1/chat/completions, after a delay taken from the last user message ("slow 3" waits 3 seconds), or fails as a provider does ("fail 401": an -authentication error). Prints its port, then serves until killed.""" +authentication error). Asked to name a session, it answers "About <the +latest user message>". Prints its port, then serves until killed.""" import json import re import sys @@ -33,6 +34,10 @@ class Handler(BaseHTTPRequestHandler): def do_POST(self): body = json.loads(self.rfile.read(int(self.headers.get("Content-Length", 0))) or b"{}") text = last_user_text(body) + if "Name this coding-agent session" in text: + said = re.findall(r"^User: (.*)$", text, re.M) + self.reply("About " + (said[-1][:40] if said else "nothing")) + return match = re.search(r"slow (\d+(?:\.\d+)?)", text) time.sleep(float(match.group(1)) if match else 0.2) failure = re.search(r"fail (\d{3})", text) @@ -43,6 +48,9 @@ class Handler(BaseHTTPRequestHandler): self.end_headers() self.wfile.write(error.encode()) return + self.reply("Done: fake reply.") + + def reply(self, text): self.send_response(200) self.send_header("Content-Type", "text/event-stream") self.send_header("Cache-Control", "no-cache") @@ -56,8 +64,7 @@ class Handler(BaseHTTPRequestHandler): self.wfile.write(f"data: {json.dumps(data)}\n\n".encode()) self.wfile.flush() - chunk({"role": "assistant", "content": "Done: "}) - chunk({"content": "fake reply."}) + chunk({"role": "assistant", "content": text}) chunk({}, "stop", {"prompt_tokens": 10, "completion_tokens": 3, "total_tokens": 13}) self.wfile.write(b"data: [DONE]\n\n") self.wfile.flush() diff --git a/tests/pi-live.sh b/tests/pi-live.sh index 3c8604d..c2d2db7 100755 --- a/tests/pi-live.sh +++ b/tests/pi-live.sh @@ -317,6 +317,46 @@ expect "a title written over keeps the name" name "Find the sidecar" expect "the menu shows it" "\"$MENU\" --print | grep -c 'Find the sidecar'" 1 t kill-window -t main:named +# Session names: from the model after the first run, refreshed every 8 of +# your messages; a name you give is kept. (The fake model names a session +# "About <your latest message>".) +t new-window -d -t main: -n auto -c "$D/work3" +t send-keys -t main:auto "pi $NO_MCP" Enter +expect "naming: an agent of its own" "st auto" idle 150 +an() { t show -pv -t main:auto @agent_name 2>/dev/null; } +said() { grep -c "\"role\":\"$1\"" "$(t show -pv -t main:auto @agent_session)" 2>/dev/null; } +say() { # message count: send it, wait for its reply + type_line auto "$1" + expect "reply $2" "said assistant" "$2" 80 +} +expect "before any message: no name" an "" +say m1 1 +expect "named after its first run" an "About m1" 80 +for i in 2 3 4 5 6 7 8; do say "m$i" $i; done +expect "not renamed within 8 of your messages" an "About m1" 30 +say m9 9 +expect "renamed at the 8th since" an "About m9" 80 +say m10 10 +type_line auto "/autoname" +expect "/autoname: renamed now" an "About m10" 80 +type_line auto "/autoname Mine now" +expect "/autoname <name>: yours" an "Mine now" 50 +for i in 11 12 13 14 15 16 17 18; do say "m$i" $i; done +sleep 2 +expect "and kept past 8 more" an "Mine now" +t kill-window -t main:auto +# A print run names its session too, before pi exits. +(cd "$D/work3" && pi -p "print me" $NO_MCP >"$D/print.out" 2>&1) +expect "a print run is named" "grep -l '\"name\":\"About print me\"' \$(ls -t \"$D\"/agent/sessions/*work3*/*.jsonl | head -1) | wc -l | tr -d ' '" 1 +# An old session never named is named when resumed. +(cd "$D/work3" && pi --no-extensions -p "an old one" $NO_MCP >"$D/old.out" 2>&1) +OLD=$(ls -t "$D"/agent/sessions/*work3*/*.jsonl | head -1) +[ "$(grep -c '"type":"session_info"' "$OLD")" = 0 ] && pass "without the extension: unnamed" || fail "the old session has a name" +t new-window -d -t main: -n old -c "$D/work3" +t send-keys -t main:old "pi --session '$OLD' $NO_MCP" Enter +expect "resumed: named from its history" "t show -pv -t main:old @agent_name 2>/dev/null" "About an old one" 150 +t kill-window -t main:old + echo "2. screen detection (pi without the extension)" t send-keys -t main:plain "PI_CODING_AGENT_DIR=$D/agent-plain pi $NO_MCP" Enter expect "identified as pi" "t show -pv -t main:plain @agent 2>/dev/null" pi 150 @@ -341,7 +381,7 @@ expect "restore resumes it by its session file" "grep -c -- \"resume .*pi --sess expect "resumed 1 of 1 agents" "grep -c '^resumed 1 of 1 agents' $D/restore.out" 1 expect "it runs again, reporting the same session" "t show -pv -t main:agent @agent_session 2>/dev/null" "$SESSION" 150 # Its last message: the first may have scrolled off a long conversation. -expect "with its conversation" "t capture-pane -p -t main:agent -S - | grep -c 'slow 1 after\$'" 1 50 +expect "with its conversation" "t capture-pane -p -t main:agent -S - | grep -cE '^ *slow 1 after\$'" 1 50 expect "and its importance" "t show -pv -t main:agent @dingger_importance 2>/dev/null" high 50 expect "and its draft, back in the input box" "t capture-pane -p -t main:agent | grep -c '^an unsent idea;'" 1 50 expect "reported again" "t show -pv -t main:agent @dingger_draft 2>/dev/null" "an unsent idea;" 30 |
