Repository navigation
Conversation
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #1428
Reproduction and root cause
Independently reproduced against current
main(e533d9b) in a separate worktree, using the new browser fixture with no component/CSS changes. At 1280×600, 19 synthetic steering messages plus retry feedback put the textarea at y=619.75–643.75: outside the visible viewport, with its hit target inaccessible. The same assertion passes with this change.Both queue maps were rendered directly into an unbounded panel. The fieldset and its chat wrapper could not shrink, while the transcript scrolled independently and the document had
overflow: hidden. Scrolling history could therefore never recover the composer controls.Implementation and trade-offs
min(180px, app viewport × 25%), using the existing--app-viewport-heightwith a100dvhfallback. Unlike plaindvh, this respects keyboards that shrink only the visual viewport.interactive-widget: resizes-contentshrinks both viewports, leaving no height difference for the keyboard marker. This covers both resize modes without hiding buttons or changing keyboard detection.No dependencies, settings, transport changes, queue management features, SDK changes, model requests or retries added. Uses existing theme and scrollbar styles. No build run in the development checkout.
Changed files
components/ChatInput.tsx,components/ChatWindow.tsx,app/globals.css: bounded queue/composer and short-viewport handling.demo/components/ChatInput.tsx,demo/components/ChatWindow.tsx,demo/app/globals.css,demo/hooks/useViewportHeight.ts: corresponding demo behavior.components/ChatInput.test.mjs: empty/3/19/50 queues, count/order/recall rendering, immutable queue data.e2e/queued-messages.mjs,e2e/run.mjs: real rendered components with intercepted agent transport/catalog, layout/hit-testing, actual command clicks, scrolling and draft assertions.e2e/README.md,docs/agents/client-platform.md: reproduction, coverage, layout constraints and remaining device-verification gaps.docs/screenshots/queued-messages-{before,after}.pngandqueued-messages-resize-{before,after}.png: synthetic-data before/after evidence for the original queue overflow and the additional layout-resize failure.Verification actually run
Tests ran with an isolated temporary HOME/agent directory and no real credentials. Provider/agent commands in the queue browser tests are intercepted, not executed.
npm testnode_modules/.bin/tsc --noEmitnpm run lintgit diff --checknpm run test:e2e(Turbopack dev server)cd demo && node_modules/.bin/tsc --noEmitcd demo && npm run lintThe queue browser regression covers 1440×900, 1366×768, 1280×600, touch 390×844, plus 400px desktop heights and 450/340/280px in two independent resize modes: visual-only shrink (including a late keyboard-height change without a resize event), and layout+visual shrink using
page.setViewportSize. The latter asserts that the keyboard marker/height override remain unset. It checks bounds, hit targets, actual Steer/Follow-up/Recall/Stop command payloads at each short height, internal overflow, first/last row access, queue growth/shrink/order, unchanged drafts, readable diagnostics, page position and restoration of the original viewport. Short idle layouts without a queue also preserve the textarea/Send and draft. Existing idle composer/model-picker regressions pass too.Expected failures recorded before the fix: original main overflow; list-cap-only candidate with long diagnostics; keyboard candidates with Stop clipped. One final rerun also encountered a pre-queue fixture route 404 in the reused Turbopack cache; after preserving
.nextin a temporary backup and rerunning from a clean dev cache, the entire suite passed. No route or test assertion was weakened to bypass it.origin/mainwas fetched again immediately before submission and remainse533d9b; no upstream changes to reconcile.Before / after
Same 1280×600 synthetic fixture, 19 steering messages and retry feedback. No user sessions, credentials or provider details.
main)Acceptance follow-up: layout viewport shrink
The first PR implementation (
7eb8a97) did not fully satisfy A08/A09. With 50 mixed queued messages, retry/long model diagnostics and a tall draft, shrinking both viewports to 390×340 put Stop at y=318.5–350.5 (outside 340px); at 390×280, Steer extended to 288.5px. The keyboard-marker-only CSS was inactive becauseinnerHeightandvisualViewport.heightshrank together.The committed regression was extended before the CSS fix and reproduced the 340px failure. Adding only short-layout CSS constraints in the app and demo makes the same test pass at 450/340/280px, without forcing a keyboard marker, hiding controls, changing
interactive-widget, or touching the hook/SDK/queue logic. Both resize modes exercise command clicks and preserve scrolling/drafts on restore.The final one-off demo check initially failed on a README image's
ERR_CONNECTION_RESETfrom GitHub's image host. Its test fixture then served the same checked-indocs/screenshot2.pnglocally and passed; no production fallback or error suppression was added.Remaining risks / unverified scenarios