Skip to content

fix(claude): expire idle picker uploads while preserving backpressure - #736

Closed
luvs01 wants to merge 7 commits into
devfrom
codex/fix-picker-upload-idle-only-20261014
Closed

luvs01 wants to merge 7 commits into
devfrom
codex/fix-picker-upload-idle-only-20261014

Conversation

@luvs01

@luvs01 luvs01 commented Oct 14, 2026 •

Copy link
Copy Markdown
Owner

Summary

Close unfinished Picker uploads after 60 seconds without body progress, before the first upstream response. Nonempty chunks reset the idle timer; upstream backpressure pauses it. Body completion, the first response, cancellation and shutdown remove it. This adds no overall upload-duration limit, and existing runtime/protocol limits still apply.

HTTP/1.1 expiry closes the underlying socket without advertising an empty success response. HTTP/2 expiry closes only the affected stream. Existing admission limits, response-stream cleanup and the eight localized Picker guides remain aligned.

Current integration

Current head: f52b83beb7a66ddc68f6f1db118d6101230f6e16.
Merged dev at 9e48f782cbac4a666b09574cb57a21be391c8d5b while preserving the original branch history. The PR was 170 commits behind that base. The two automatically merged files were inspected; the proposal remains 12 files, +289/-5 relative to that base. No timeout policy, scan configuration or assertion was relaxed.

Verification

Current integrated tree: 4d794af5beeb6f0ba4228b27c359099077ee7656. Its GitHub tree was verified to match the locally tested tree.

Bun 1.4.4, Linux:

bun test tests/claude-integration/claude-picker-upload.test.ts tests/claude-integration/claude-picker-listener.test.ts tests/claude-integration/claude-picker-linger.test.ts
bun run typecheck
bun scripts/structure-ssot.ts
bun scripts/privacy-scan.ts
bun test tests/ci-workflows/file-size-ratchet.test.ts
git diff --check 9e48f782cbac4a666b09574cb57a21be391c8d5b
cd docs-site && bun install --frozen-lockfile && bun run build
  • Actual TLS regressions: 83 passed, 0 failed, 492 assertions. Coverage includes progressing and stalled uploads, request-side backpressure, HTTP/1.1 failure without a 200 response, HTTP/2 cancellation, healthy sibling streams and recovered admission.
  • Typecheck, structure, privacy and whitespace checks passed; size-ratchet coverage passed 9 tests / 85 assertions.
  • Frozen dependencies matched the integrated lockfiles. The actual documentation build passed 593 pages / 84,977 internal links.
  • The initial sandbox disallowed loopback listening (EPERM); the permitted loopback run passed. This is controlled local TLS evidence.
  • Full local repository testing was impractical with three concurrent worktrees. The AGENTS.md resource exception was used with focused behavior tests and typecheck. No complete local suite success is claimed.

Current-head hosted checks

All checks applicable to this head passed:

  • Cross-platform CI: all four Ubuntu test shards and the final ci gate passed, along with type/lint/build gates, the documentation build, structure/storage/API checks, npm-global and Docker smoke.
  • Catalog async contracts: passed.
  • CodeQL: Actions, JavaScript/TypeScript, Python and the aggregate result passed.
  • Current-head target/description hygiene passed. All four inline review threads are resolved.

CodeRabbit skipped its automatic review after the Ready transition because this repository has fewer than ten stars. Its successful status is not counted as a fresh review of this head; the independent final-tree review is described below.

The workflow skipped native macOS/Windows and Desktop-only jobs under its existing PR/path policy. Those skips are not native-platform acceptance evidence.

The older CodeQL run 40339832919 failed during Actions/Python result upload. That historical result is retained; the new head completed all three analyses successfully without weakening scan coverage.

Review scope and remaining acceptance

All four existing inline findings were addressed before this integration. A fresh read-only code review found no additional timer, backpressure, cleanup or admission defect.

The upstream maintainer's condition remains a separate acceptance question: reproduce a real claude.ai upload stall that its own timeout does not already cover, and decide whether the 60-second default policy is appropriate. The controlled fixtures do not establish that live-edge behavior. Installed Claude Desktop macOS/Windows acceptance, sustained client churn and explicit maintainer approval are not claimed.

This fork review concerns the implemented idle-only candidate and its evidence. Review readiness does not record upstream policy acceptance, deployment or merge approval.

Checklist

  • Scope stays focused and avoids unrelated cleanup.
  • Docs or release notes were updated when needed.
  • Security-sensitive changes were reviewed for secrets, auth, and unsafe defaults.

Summary by CodeRabbit

  • New Features

    • Picker uploads that make no progress for 60 seconds before the first upstream response are interrupted without a success response; HTTP/2 resets only the affected stream.
    • The idle timer pauses during upstream backpressure and clears when an upload completes or the first upstream response arrives.
    • The timeout does not limit total upload duration or apply to response streams. Existing runtime and protocol limits remain in effect.
  • Documentation

    • Updated Claude Code and Claude Desktop guides to describe the timeout behavior.

Publish the exact locally tested candidate tree. See the draft PR for
focused validation, remaining native/operational coverage and acceptance holds.
@coderabbitai

coderabbitai Bot commented Oct 14, 2026 •

Copy link
Copy Markdown

Review in Change Stack →

No actionable comments were generated in the recent review.

Recent review info
Run configuration
Commits

Reviewing files that changed from the base of the PR and between 78107b4 and f52b83b.

Files selected for processing: 11
  • docs-site/src/content/docs/fr/guides/claude-code.md
  • docs-site/src/content/docs/guides/claude-code.md
  • docs-site/src/content/docs/ja/guides/claude-code.md
  • docs-site/src/content/docs/ko/guides/claude-code.md
  • docs-site/src/content/docs/ru/guides/claude-code.md
  • docs-site/src/content/docs/tr/guides/claude-code.md
  • docs-site/src/content/docs/zh-cn/guides/claude-code.md
  • docs-site/src/content/docs/zh-tw/guides/claude-code.md
  • src/claude/intercept/picker-listener.ts
  • structure/clients/claude-desktop.md
  • tests/claude-integration/claude-picker-upload.test.ts

Included review availability: This review used your included allowance. Your plan provides up to 1 included review per hour; 0 remain after this review.

Walkthrough

The picker relay now closes uploads that make no progress for 60 seconds before the first upstream response. The timer pauses during upstream backpressure and clears when the upload completes or the upstream responds. HTTP/1 and HTTP/2 tests and documentation cover this behavior.

Changes: Picker upload idle timeout

Layer / File(s) Summary
Configure and enforce the upload idle timer
src/claude/intercept/picker-listener.ts
The listener adds an optional uploadIdleMs setting and a 60-second default. It arms and rearms the timer on upload progress, pauses it during backpressure, and clears it on completion or the first upstream response. On expiry, it marks the client gone, logs the timeout, and stops the unfinished upload.
Observe and validate backpressure behavior
tests/helpers/picker-upload-backpressure.ts, tests/claude-integration/claude-picker-upload.test.ts
The tests observe HTTP/1 and HTTP/2 flow-control events. They verify stalled uploads time out, progressing uploads deliver all bytes, response streams remain open, and backpressure pauses the idle timer until reads resume.
Document timeout and cleanup behavior
structure/clients/claude-desktop.md, docs-site/src/content/docs/guides/claude-code.md, docs-site/src/content/docs/{fr,ja,ko,ru,tr,zh-cn,zh-tw}/guides/claude-code.md
The documentation describes the 60-second pre-response idle timeout, backpressure handling, cleanup behavior, and the timeout’s exclusions.

Priority: Normal

Estimated code review effort: 3 (Moderate) | ~25 minutes

Change: Bug fix

Sequence Diagram(s)

sequenceDiagram
  participant Client
  participant PickerListener
  participant Upstream
  Client->>PickerListener: Send upload data
  PickerListener->>Upstream: Relay upload data
  Upstream-->>PickerListener: Apply backpressure
  PickerListener->>PickerListener: Pause idle timer
  Upstream-->>PickerListener: Resume reading or send first response
  PickerListener->>PickerListener: Resume or clear idle timer
  PickerListener->>Client: On timeout, close without success response
Loading

Suggested reviewers: lidge-jun, ingwannu

Merge Risk: Minimal · up to f52b8

No actionable issue is established for this change. The separate live-upload and platform acceptance work remains outside this code-risk assessment.

Pre-merge checks: Passed 4
Check name Status Explanation
Title check Passed The title "fix(claude): expire idle picker uploads while preserving backpressure" matches the main change. The changeset adds a 60-second pre-response idle timer for picker uploads in src/claude/inter…
Linked Issues check Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check Passed Check skipped because no linked issues were found for this pull request.
Description Check Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Full details: Title check

Explanation

The title "fix(claude): expire idle picker uploads while preserving backpressure" matches the main change. The changeset adds a 60-second pre-response idle timer for picker uploads in src/claude/intercept/picker-listener.ts, pauses it under upstream backpressure, and adds tests and helpers plus docs for the new behavior. The title is specific, concise, and follows a conventional commit style. It does not cover HTTP/2 stream reset or the closeInput socket change, which is expected for a short title.

Finishing Touches
📝 Generate docstrings
  • Commit to this branch
  • Create a new PR
🧪 Generate unit tests (beta)
  • Commit to this branch
  • Create a new PR
  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@github-actions

github-actions Bot commented Oct 14, 2026 •

Copy link
Copy Markdown

✅ Deterministic PR hygiene checks passed.

@github-actions github-actions Bot added the bug Something isn't working label Oct 14, 2026
@luvs01
luvs01 marked this pull request as ready for review October 14, 2026 01:13
@luvs01

luvs01 commented Oct 14, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai review

@coderabbitai

coderabbitai Bot commented Oct 14, 2026 •

Copy link
Copy Markdown
✅ Action performed

Review finished.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

coderabbitai[bot]

This comment was marked as resolved.

@luvs01
luvs01 marked this pull request as draft October 21, 2026 02:41
devin-ai-integration[bot]

This comment was marked as resolved.

devin-ai-integration[bot]

This comment was marked as resolved.

luvs01 commented Oct 21, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai full review

Please review the complete current head 78107b447427150fc9123cbd592f968285267064 against dev@12025981e5a304cdb6b1b54f525ba8554f623977. The top-level assessment still identifies 3d9a7274 as its covered commit. All four observed inline threads are resolved, and the follow-up includes the relocated Picker guide paragraphs plus actual request-side h1/h2 backpressure coverage and its continuous-pause observer correction.

Exact-head fork CI 39538129949 completed successfully, including all four Ubuntu test shards. This is not a request to waive the 60-second policy decision, live Desktop/native-platform acceptance, or maintainer security review. Keep Draft while those gates remain open. No linked public issue is being invented; this is the scoped idle-only follow-up to the previously discussed Picker proposal, and the private investigation is not copied into the repository.

@coderabbitai

coderabbitai Bot commented Oct 21, 2026 •

Copy link
Copy Markdown
✅ Action performed

Full review finished.

@luvs01 luvs01 changed the title fix(claude): expire idle picker uploads without a lifetime cap fix(claude): expire idle picker uploads while preserving backpressure Oct 22, 2026
Preserve the published PR history while integrating dev 9e48f78. Retain the idle-only policy, request backpressure handling and response cleanup.

Validation: Bun 1.4.4, 83 focused TLS tests; typecheck, structure, privacy, file-size gates and 593-page documentation build passed.
@luvs01
luvs01 marked this pull request as ready for review October 27, 2026 00:32
@luvs01

luvs01 commented Oct 27, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai review

@coderabbitai

coderabbitai Bot commented Oct 27, 2026 •

Copy link
Copy Markdown
✅ Action performed

Review finished.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

luvs01 commented Oct 27, 2026

Copy link
Copy Markdown
Owner Author

The reviewed 12-file candidate is preserved unchanged at f52b83beb7a66ddc68f6f1db118d6101230f6e16 (tree 4d794af5) in the canonical review copy, whose applicable CI has passed. Closing this duplicate review thread while retaining the head branch, which remains in use. This records transfer for review, not a merge or live-edge acceptance.

@luvs01 luvs01 closed this Oct 27, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant