fix(desktop): surface Buzz Term attach failures instead of a blank panel - #5427
fix(desktop): surface Buzz Term attach failures instead of a blank panel#5427Glucksberg wants to merge 3 commits into
Conversation
An attach failure removed the tab and set available=false with only a console.error — unreachable in a production build, which has no devtools and, on Windows, no log file. The user got a bare gray panel with a dead + button and nothing to report (block#4930). Render the failure in the viewport instead: 'Terminal unavailable: <error>' with a Retry action, carrying the backend's own message rather than a generic string. On Windows before block#5425 that reads 'CreateProcessW "cmd.exe" in cwd None failed ... (os error 2)' — the error the panel already had and was throwing away. Retry clears it and re-enables the auto-create path. No notice for a missing channel context: the Cmd/Ctrl+J toggle refuses to open the panel without one, and an effect closes the panel if the channel goes away, so such a notice could only flash during navigation. Covered by TerminalBootstrap unit tests (notice rendering, and retry re-attaching after a failed attach) and a Playwright screenshot spec that drives the real attach-failure path end to end via the mock bridge, which does not implement terminal_attach. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Signed-off-by: Glucksberg <glucksberg89@gmail.com>
Before — the silent panelAttach fails, the session is removed, After — the failure is the UIThe backend's own error text, plus a Retry that clears it and re-runs the auto-create path. The error string here is the e2e mock bridge's ( Both images are |
Signed-off-by: Glucksberg <glucksberg89@gmail.com>
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: a649d72e26
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
| if (attachRetryRequestedRef.current) { | ||
| attachRetryRequestedRef.current = false; | ||
| createSession(); |
There was a problem hiding this comment.
Retry the attachment in its original channel
When an attachment fails in channel B, failedAttachRef records only a global boolean. If the user navigates to channel A, which already has a healthy terminal, before clicking Retry, this effect calls createSession() with contextRef.current for A, spawning an unwanted extra shell there while the failed B attachment remains unretried until the user returns to B. Associate the retry with the failed channel/context, or only force creation when the current channel is the one whose attachment failed.
Useful? React with 👍 / 👎.
Signed-off-by: Glucksberg <glucksberg89@gmail.com>
f275713 to
72805dd
Compare


Summary
When the Term panel fails to attach, it renders nothing — a blank body with a
+button that does nothing.TerminalBootstrap.fail()removes the session, setsavailable = false, and reports the error toconsole.error. In a production build there is no devtools to read that, and on Windows there is no log file either, so the error the backend produced is simply discarded on the way to the user.That is the surface #4930 was reported through: the reporter saw a permanently blank Term panel and had nothing to attach to the issue except a Windows Event Log entry. The backend had a precise, actionable error the whole time —
CreateProcessW "cmd.exe" in cwd None failed … (os error 2)— and the UI threw it away.This renders that error in the viewport instead, with a Retry action that clears it and re-runs the auto-create path.
Before / after
Screenshots in the first comment. Both are the same element (
.buzz-terminal-substrate) at the same viewport, so they're directly comparable.Why there is no notice for "no channel selected"
An earlier version of this change also rendered
"Select a channel to open a terminal."when the panel had no channel context. That state is not reachable, and shipping the notice would have been a small regression:TerminalBootstrap.tsx— the Cmd/Ctrl+J toggle returns early when!context, so the panel cannot be opened without a channel.contextgoes away while it is open.So the only way to render that notice is the single frame between navigating away from a channel and the effect running. That's a flash during navigation, not a state a user can be in. The existing test
a non-channel route closes the panel and ignores the terminal shortcutalready asserts this behaviour. The notice is now scoped to the one case that genuinely occurs:!available.Relationship to #5425
Related, not a duplicate, and they fix different things.
Neither subsumes the other. With #5425 merged, a Windows user shouldn't reach the failure path by that route — but any future attach failure, on any platform, is silent again without this change. They can merge in either order; they touch no common files.
Related issue
Related to #4930 — this addresses the "Term panel renders permanently blank" symptom, which #5425 explicitly leaves out of scope. Deliberately not marked
Fixes, since the root cause of that issue is the backend spawn failure, not this rendering gap.Searched for duplicates: no other open PR touches
desktop/src/features/terminal.The issue's remaining item — "the desktop currently writes no log files on Windows" — is not addressed here.
Testing
TerminalBootstrap.test.mjs, 10/10): the notice renders with the backend's own error text, and Retry re-attaches after a failure. Full desktop JS suite: 4536/4536.term-empty-states-screenshots.spec.ts, registered in thesmokeproject): drives the real attach-failure path end to end. The mock bridge doesn't implementterminal_attach, so the panel takes the genuine failure route rather than a stubbed one — the notice, its text, and the Retry button are all asserted before the capture.pnpm check(biome, file sizes, px-text, pubkey truncation) andpnpm typecheckclean.One note on reading the screenshot: the error string in it is the mock bridge's (
Unsupported mocked Tauri command: terminal_attach), because that is what fails in an e2e build. On Windows the same slot carries the realCreateProcessW …error. The point of the shot is that whatever the backend said now reaches the user.