From f822709d6e5c1b94d80e014c55904a0a0754e1a4 Mon Sep 17 00:00:00 2001 From: Adolanium <94890352+Adolanium@users.noreply.github.com> Date: Thu, 27 Aug 2026 20:01:05 +0300 Subject: [PATCH 1/2] fix(web): use the drawer close fallback for right-panel terminals Drawer close already writes exit if terminalClose fails, so the process dies. Right-panel close only hid the session. A failed close left a running PTY, and a reload brought the closed terminal back. Route panel close and panel-surface cleanup through the same close path the drawer uses. --- apps/web/src/components/ChatView.tsx | 23 ++++------------------- 1 file changed, 4 insertions(+), 19 deletions(-) diff --git a/apps/web/src/components/ChatView.tsx b/apps/web/src/components/ChatView.tsx index f0188af478c0..52b81546dcee 100644 --- a/apps/web/src/components/ChatView.tsx +++ b/apps/web/src/components/ChatView.tsx @@ -3623,17 +3623,12 @@ function ChatViewContent(props: ChatViewProps) { const closePanelTerminal = useCallback( (terminalId: string) => { if (!activeThreadRef || activeRightPanelSurface?.kind !== "terminal") return; - void closeTerminalMutation({ - environmentId: activeThreadRef.environmentId, - input: { threadId: activeThreadRef.threadId, terminalId, deleteHistory: true }, - }); - storeCloseTerminal(activeThreadRef, terminalId); + closeTerminal(terminalId); useRightPanelStore .getState() .closeTerminal(activeThreadRef, activeRightPanelSurface.id, terminalId); - setTerminalFocusRequestId((value) => value + 1); }, - [activeRightPanelSurface, activeThreadRef, closeTerminalMutation, storeCloseTerminal], + [activeRightPanelSurface, activeThreadRef, closeTerminal], ); const requestCloseTerminal = useCallback( (terminalId: string) => { @@ -3697,22 +3692,12 @@ function ChatViewContent(props: ChatViewProps) { } if (surface.kind === "terminal") { for (const terminalId of surface.terminalIds) { - storeCloseTerminal(activeThreadRef, terminalId); - void closeTerminalMutation({ - environmentId: activeThreadRef.environmentId, - input: { threadId: activeThreadRef.threadId, terminalId, deleteHistory: true }, - }); + closeTerminal(terminalId); } } } }, - [ - activeThreadRef, - activePreviewState.sessions, - closePreview, - closeTerminalMutation, - storeCloseTerminal, - ], + [activeThreadRef, activePreviewState.sessions, closePreview, closeTerminal], ); const syncActivePreviewSurface = useCallback(() => { if (!activeThreadRef) return; From 11293b843cb7e0854192283cd4026bc9bdcecaee Mon Sep 17 00:00:00 2001 From: Adolanium <94890352+Adolanium@users.noreply.github.com> Date: Thu, 27 Aug 2026 20:12:06 +0300 Subject: [PATCH 2/2] fix(web): do not steal composer focus when closing panel tabs Panel surface cleanup was going through closeTerminal, which also bumps terminal focus. Closing other right-panel tabs could then focus the bottom drawer PTY. Keep the exit fallback on a helper with no focus bump. Drawer and explicit panel-tab close still bump focus. Cleanup uses the helper only. --- apps/web/src/components/ChatView.tsx | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/apps/web/src/components/ChatView.tsx b/apps/web/src/components/ChatView.tsx index 52b81546dcee..17bb20d58340 100644 --- a/apps/web/src/components/ChatView.tsx +++ b/apps/web/src/components/ChatView.tsx @@ -3115,7 +3115,7 @@ function ChatViewContent(props: ChatViewProps) { gitCwd, storeNewTerminal, ]); - const closeTerminal = useCallback( + const closeTerminalSession = useCallback( (terminalId: string) => { if (!activeThreadId || !activeThreadRef) return; const fallbackExitWrite = () => @@ -3137,7 +3137,6 @@ function ChatViewContent(props: ChatViewProps) { } })(); storeCloseTerminal(activeThreadRef, terminalId); - setTerminalFocusRequestId((value) => value + 1); }, [ activeThreadId, @@ -3148,6 +3147,13 @@ function ChatViewContent(props: ChatViewProps) { writeTerminal, ], ); + const closeTerminal = useCallback( + (terminalId: string) => { + closeTerminalSession(terminalId); + setTerminalFocusRequestId((value) => value + 1); + }, + [closeTerminalSession], + ); const runProjectScript = useCallback( async ( script: ProjectScript, @@ -3692,12 +3698,12 @@ function ChatViewContent(props: ChatViewProps) { } if (surface.kind === "terminal") { for (const terminalId of surface.terminalIds) { - closeTerminal(terminalId); + closeTerminalSession(terminalId); } } } }, - [activeThreadRef, activePreviewState.sessions, closePreview, closeTerminal], + [activeThreadRef, activePreviewState.sessions, closePreview, closeTerminalSession], ); const syncActivePreviewSurface = useCallback(() => { if (!activeThreadRef) return;