fix: stop consuming OpenAI Responses stream after the terminal event - #217
Conversation
|
@yexisu is attempting to deploy a commit to the vastsa's projects Team on Vercel. A member of the Team first needs to authorize it. |
vastsa
left a comment
There was a problem hiding this comment.
Reviewed against the current main and the pinned @earendil-works/pi-ai@0.85.1 implementation. The issue is real: processResponsesStream finalizes response.completed/response.incomplete but otherwise keeps iterating, while the OpenAI SDK aborts the request when that iterator is broken. The pnpm patch is applied by a frozen-lockfile install, and the regression fixture hangs after the terminal SSE event as intended.
Validation: agent-runtime targeted test passed; full agent-runtime suite passed (27 files / 348 tests); agent-runtime typecheck and build passed; docs locale check passed; PR CI passed JS build/typecheck/lint/test, Rust host-core test, and docs locale pair check.
No merge-blocking issues found. The dedicated live-proxy E2E-248 remains Draft with no executable test script, so it is not independently covered beyond the regression test. Vercel is only failing because team authorization is required.
Fixes #130
Problem
When talking to an OpenAI Responses-compatible endpoint, the client keeps consuming the SSE stream after receiving
response.completed. Upstream@earendil-works/pi-ai@0.85.1(processResponsesStreaminopenai-responses-shared.js) only finishes when the server closes the connection. If the backend or a reverse proxy (e.g. Nginx) holds the idle connection open instead of sending a TCP FIN, the turn hangs forever and the agent cannot continue.Fix
Add a pnpm patch on
@earendil-works/pi-ai@0.85.1that breaks out of the event loop right afterfinalizeResponseruns forresponse.completed/response.incomplete. The consumer stops iterating, the OpenAI SDK aborts the underlying request, and the turn completes immediately without depending on the server closing the connection.The Codex Responses adapter already returns on the terminal event, so it is unaffected.
Test
responses-stream-termination.test.ts: a stub fetch returns an SSE body that emitsresponse.completedand then never ends; the stream resolves withstopReason: "stop"and correct usage instead of hanging.packages/agent-runtime: 27 test files / 348 tests pass.The patch can be dropped once a pi-ai release ships the fix upstream.