diff options
| author | Adam Malczewski <[email protected]> | 2026-05-28 10:33:33 +0900 |
|---|---|---|
| committer | Adam Malczewski <[email protected]> | 2026-05-28 10:33:33 +0900 |
| commit | 2eeabc95b78f6624c187e1e3892f9413266b4b9a (patch) | |
| tree | ffdcd754bafb4da036b1fd3dfb22617754067641 /packaging/[email protected] | |
| parent | 1e70f2d12274da833035912206b1ac0b1ee57ef1 (diff) | |
| download | dispatch-2eeabc95b78f6624c187e1e3892f9413266b4b9a.tar.gz dispatch-2eeabc95b78f6624c187e1e3892f9413266b4b9a.zip | |
fix(core): strip stale [USER INTERRUPT] from LLM history; inject into last tool of batch
The interrupt block embedded in a tool-result was persistent in the
assistant message history, so the imperative 'You MUST address these
before continuing' got re-evaluated as fresh on every subsequent LLM
step. Result: the model repeatedly thought about and re-acknowledged
the same interrupt 5-10+ times per chat (verified in production DB
traces — e.g. tab 4c5727aa had 11 thinking chunks quoting a single
interrupt verbatim).
agent.ts (toModelMessages): strip [USER INTERRUPT] from every tool-
result except the one in the freshest tool-batch (last chunk of the
last assistant message, which itself must be the last message). The
strip is a serialization-time transform only — this.messages, the DB
row, and the UI display all keep the full text. The LLM sees the
imperative exactly once: the step immediately after injection.
agent.ts (tool execution loop): batch queued messages across the
group's tool calls and inject them only into the LAST executable tool's
result. Previously the first tool to dequeue won; now the interrupt
lands in a single deterministic spot regardless of timing. Tool-level
handlers (run-shell/youtube/retrieve) are untouched — they still embed
their own interrupt text when they background work.
Also fix pre-existing tabs.test.ts: it referenced a getDescendantIds
function that didn't exist (added: BFS, leaf-first, cycle-safe, skips
archived) and imported bun:sqlite directly which vite couldn't resolve
(rewrote with a minimal FakeDatabase + vi.mock pattern matching the
rest of the suite).
Diffstat (limited to 'packaging/[email protected]')
0 files changed, 0 insertions, 0 deletions
