Skip to content

fix(agent): close proxy ingest upload per batch so events stream live#3043

Merged
charlesvien merged 1 commit into
mainfrom
fix/ingest-per-batch-upload
Jul 1, 2026
Merged

fix(agent): close proxy ingest upload per batch so events stream live#3043
charlesvien merged 1 commit into
mainfrom
fix/ingest-per-batch-upload

Conversation

@charlesvien

@charlesvien charlesvien commented Jul 1, 2026

Copy link
Copy Markdown
Member

Problem

Cloud task runs stream agent output to the browser through the agent-proxy: the sandbox POSTs events to the proxy ingest endpoint (write leg), the proxy writes them to a Redis stream, and the browser consumes them over SSE (read leg). The read leg works, but live output never showed up on the proxy write leg — the browser sat on keepalives and then received the whole turn in one burst (or on refresh from persisted history).

Root cause is the write leg's transport. The ingest sender streams events into a single long-lived chunked POST that stays open until the stream window rolls. The ingress in front of the proxy buffers the request body and only forwards it once the request closes, so the proxy receives nothing until the upload rolls. Streaming a response (SSE) is well supported; dribbling bytes into a long-lived request body is not — intermediaries buffer it. The tell: the empty bounded sequence-sync probe always arrives immediately, while the long-lived content upload doesn't land until it closes.

Changes

After a flush drains the buffer, close the active upload instead of holding it open, gated to the proxy write leg (usingProxy). Each drained batch now rides its own promptly-closed request, so a buffering ingress forwards it within a round-trip and delivery is effectively live. Sequencing, backpressure, 409 rebase and restart-resume are unchanged — only the moment we close the upload moved.

This supersedes the short-window stopgap from #3042: per-batch close makes a shortened proxy window redundant (the upload closes per batch, so a window never trips), so DEFAULT_PROXY_STREAM_WINDOW_MS is removed and the window default is a single value again.

Scope is limited to the proxy path on purpose:

  • Proxy write leg (usingProxy): close per batch → live delivery.
  • Django path: untouched — keeps its existing long-lived upload and window.
  • Stop path: unchanged — still writes the completion line onto a final upload via drainForStop (that path runs under stopped, where the new close is skipped).

How did you test this?

I'm an agent (Claude Code), human-directed. Automated tests I actually ran, all green:

  • vitest run src/server/event-stream-sender.test.ts (17 pass). Replaced the old "keeps the active ingest request open across scheduled flushes" case — that held-open behavior was the bug — with "closes the active ingest upload after each drained batch on the proxy path", which drives the proxy path and asserts each batch is delivered and closed before stop() while the completion line rides a final upload. The Django-path cases (no eventIngestBaseUrl) are unchanged and still pass, confirming the gate.
  • tsc --noEmit and biome check on the changed files — clean.

I did not run a full sandbox-to-browser flow in a live environment.

Automatic notifications

  • Publish to changelog?
  • Alert Sales and Marketing teams?

@greptile-apps

greptile-apps Bot commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

Reviews (1): Last reviewed commit: "close ingest upload after each drained b..." | Re-trigger Greptile

@charlesvien charlesvien force-pushed the fix/ingest-per-batch-upload branch from 3e40b24 to 3623e13 Compare July 1, 2026 02:22
@charlesvien charlesvien marked this pull request as ready for review July 1, 2026 02:22
@charlesvien charlesvien added the Stamphog This will request an autostamp by stamphog on small changes label Jul 1, 2026
@github-actions

github-actions Bot commented Jul 1, 2026

Copy link
Copy Markdown

React Doctor found no issues in the changed files. 🎉

Reviewed by React Doctor for commit 3623e13.

@charlesvien charlesvien changed the title fix(agent): close ingest upload per batch so events aren't buffered fix(agent): close proxy ingest upload per batch so events stream live Jul 1, 2026

@github-actions github-actions Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Clean, well-reasoned fix that replaces a 1-second timer-based proxy stream close with an immediate per-batch close, correctly guarded from the stop path. No data model, API contract, dependency, or infra changes.

@greptile-apps

greptile-apps Bot commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

Reviews (2): Last reviewed commit: "close ingest upload after each drained b..." | Re-trigger Greptile

@charlesvien charlesvien merged commit 06f1d07 into main Jul 1, 2026
30 of 31 checks passed
@charlesvien charlesvien deleted the fix/ingest-per-batch-upload branch July 1, 2026 02:37
charlesvien added a commit that referenced this pull request Jul 1, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Stamphog This will request an autostamp by stamphog on small changes

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant