fix(chat): cancel orphaned generation on client disconnect
Closing the QuickChat browser tab mid-response left the backend agent
running with no listener. The `activeGenerations` slot persisted and the
next message's freshly-opened CLI SessionManager raced against the
lingering agent on the same session file, so the model produced no
output for the new prompt.
- POST /chat/sessions/:id/messages now calls cancelGeneration on
req.on("close") if the response hasn't ended yet, so disconnects stop
the agent promptly.
- beginGeneration only aborts the prior controller; it no longer
disposes the prior agent. Disposing pre-emptively could yank the CLI
process out from under the new generation's session opened on the
same file.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -560,6 +560,15 @@ export function registerChatRoutes(ctx: ApiRoutesContext, deps: ChatRouteDeps):
|
||||
// Handle client disconnect
|
||||
req.on("close", () => {
|
||||
unsubscribe();
|
||||
// If the response hasn't been ended (i.e. the generation was still
|
||||
// streaming when the browser disconnected — tab close, navigation,
|
||||
// network drop), cancel the agent so it doesn't keep running with
|
||||
// nobody listening. Otherwise the next request for this session sees a
|
||||
// stale `activeGenerations` entry and races against the lingering
|
||||
// agent for the same CLI session file.
|
||||
if (!res.writableEnded) {
|
||||
chatManager.cancelGeneration(sessionId);
|
||||
}
|
||||
});
|
||||
|
||||
// Send heartbeat every 30s to keep connection alive
|
||||
|
||||
Reference in New Issue
Block a user