fix(tui): strip ANSI from input buffer after gateway pipe break (#28419) - #29252
fix(tui): strip ANSI from input buffer after gateway pipe break (#28419)#29252Jiahui-Gu wants to merge 1 commit into
Conversation
…Research#28419) When the TUI gateway's stdout pipe breaks mid-render and the gateway auto-restarts, rendering ANSI bytes (color codes, cursor moves, OSC title sets) can leak onto stdin and be delivered to the composer as if the user had typed them. The bug report shows the input box flooded with strings like "102;71M5;104;62M5;106;60M..." — the tail end of de-escaped CSI parameter lists whose ESC prefix was consumed earlier in the byte stream. Add stripAnsiSequences() and apply it at every paste-like input path in TextInput: - the bracketed-paste branch (after BRACKET_PASTE marker removal) - flushPaste() - pastePlainText() (OS clipboard / right-click paste) The helper strips full CSI / OSC / SS3 / two-byte ESC sequences and, when the residue still has the unmistakable shape of an orphan CSI param flood (multiple "<digits>;<digits>;<digits><letter>" chains), runs an iterative cleanup pass to remove the leftover digits, semicolons and stray CSI final bytes. Ordinary user text like "a; b; c" or "color: red;" is preserved because the aggressive pass only fires when the orphan-flood signature is present. Co-Authored-By: Claude Opus 4 (1M context) <noreply@anthropic.com>
|
FYI for maintainer triage: noticed there's another open PR #28463 ( This PR specifically strips ANSI sequences from the input buffer ( |
|
Closing as redundant against current This is part of the TUI/CLI ANSI/SGR/escape-leak cluster, most of which is already solved on
Your work here overlapped this already-merged coverage. Thanks for the contribution and for helping surface the leak class — it's appreciated. |
Summary
Fixes #28419. When the TUI gateway pipe breaks and the gateway auto-restarts, render bytes from stdout can leak into stdin. The composer's TextInput previously stripped only bracketed-paste markers (
ESC[200~/ESC[201~), so anything between them — including chunked / de-escaped CSI sequences like35;104;62m— slipped throughPRINTABLEand ended up in the input field, producing the characteristic ANSI flood reported in the issue.Fix
ui-tui/src/components/textInput.tsx:stripAnsiSequences()helper that strips full CSI / OSC / SS3 / two-byte-ESC / bare-ESC / C0+C1 control bytes.\d+;\d+;\d+[A-Za-z]chains), an iterative cleanup pass removes leftover digits,;, and stray CSI final letters. Ordinary user text (a; b; c,color: red;,12;34) is preserved because the aggressive pass only fires when the orphan-flood signature is present.useInput,flushPaste(), andpastePlainText().Test plan
ui-tui/src/__tests__/textInputAnsiStrip.test.ts— 8 cases including the exact garbage shape from the bug report (102;71M5;104;62M...→\"\"), bracketed-paste-wrapped ANSI leaks, unicode/punctuation preservationvitest runshows no new regressions (2 pre-existing failurescursorDriftRegression,ink-resizealso fail on main)tsc --noEmitclean🤖 Generated with Claude Code