Skip to content

Conversation

@RussellZager
Copy link

@RussellZager RussellZager commented Feb 10, 2026

Related GitHub Issue

Closes: #10699

Description

This PR implements inline terminal rendering parity with the VSCode Terminal, addressing the issue where raw ANSI bracket codes (e.g., [32m, [1m) were displayed instead of colors and formatting.

Key Changes:

  • Backend (src/integrations/terminal/TerminalProcess.ts):

    • Replaced the aggressive strip-ansi usage with a custom removeVSCodeShellIntegration method. This explicitly removes VSCode-specific shell integration sequences (OSC 633, OSC 133) but preserves standard ANSI SGR sequences (colors, formatting).
    • Added stripCursorSequences to remove unsupported cursor movement codes (e.g., clear line, move cursor) to keep the output clean for the webview.
  • Frontend (webview-ui/src/components/chat/TerminalOutput.tsx):

    • Created a new TerminalOutput component utilizing the ansi-to-html library.
    • Maps standard ANSI colors to VSCode terminal CSS variables (e.g., var(--vscode-terminal-ansiGreen)), ensuring the output automatically adapts to the user's active color theme.
    • Enabled escapeXML: true to prevent XSS vulnerabilities from command output.
  • Integration: Updated CommandExecution.tsx to use TerminalOutput instead of the generic CodeBlock for displaying command output.

Test Procedure

  1. Backend Unit Tests:

    • Created src/integrations/terminal/__tests__/TerminalProcess.test.ts to verify that removeVSCodeShellIntegration strictly removes OSC sequences while keeping ANSI colors intact, and that stripCursorSequences removes cursor control codes.
    • Updated src/integrations/terminal/__tests__/TerminalProcessExec.bash.spec.ts to assert that simulated terminal commands return string output containing ANSI codes (e.g., \x1B[31mRed Text\x1B[0m) rather than stripped plain text.
  2. Frontend Unit Tests:

    • Created webview-ui/src/components/chat/__tests__/TerminalOutput.spec.tsx to verify:
      • Plain text rendering.
      • ANSI-to-HTML conversion (checking for styled spans).
      • XSS prevention (ensuring HTML tags in output are escaped).
  3. Regression Testing:

    • Ran full test suite (npm test) to ensure no regressions in existing terminal or chat functionality.

Pre-Submission Checklist

  • Issue Linked: This PR is linked to an approved GitHub Issue (see "Related GitHub Issue" above).
  • Scope: My changes are focused on the linked issue (one major feature/fix per PR).
  • Self-Review: I have performed a thorough self-review of my code.
  • Testing: New and/or updated tests have been added to cover my changes (if applicable).
  • Documentation Impact: I have considered if my changes require documentation updates (see "Documentation Updates" section below).
  • Contribution Guidelines: I have read and agree to the Contributor Guidelines.

Documentation Updates

  • No documentation updates are required.

Additional Notes

  • Dependency: Added ansi-to-html to webview-ui dependencies (approx. 3KB gzipped impact).
  • Security: The implementation uses escapeXML: true in the converter to sanitize output before rendering via dangerouslySetInnerHTML.

Get in Touch

tea_earl_grey_hot


Important

This PR enhances terminal output rendering by preserving ANSI codes, introducing a new TerminalOutput component, and updating tests for improved functionality and security.

  • Behavior:
    • Replaces strip-ansi with removeVSCodeShellIntegration in TerminalProcess.ts to preserve ANSI SGR sequences while removing VSCode-specific sequences.
    • Adds stripCursorSequences to remove unsupported cursor movement codes.
    • Updates CommandExecution.tsx to use TerminalOutput for command output.
  • Components:
    • Adds TerminalOutput component in TerminalOutput.tsx using ansi-to-html for ANSI to HTML conversion.
    • Maps ANSI colors to VSCode terminal CSS variables for theme consistency.
  • Tests:
    • Adds TerminalProcess.test.ts to test ANSI handling functions.
    • Updates TerminalProcessExec.bash.spec.ts to verify ANSI codes are preserved.
    • Adds TerminalOutput.spec.tsx to test TerminalOutput rendering and XSS prevention.
    • Updates CommandExecution.spec.tsx to test integration with TerminalOutput.

This description was created by Ellipsis for 64258da. You can customize this summary. It will automatically update as commits are pushed.

google-labs-jules bot and others added 2 commits February 10, 2026 02:24
Fixes RooCodeInc#10699

## Problem
The inline terminal output displayed raw ANSI bracket codes ([1m, [32m, etc.)
instead of rendering colors and formatting. This was caused by:
1. Backend: strip-ansi removing the ESC byte but leaving bracket remnants
2. Frontend: CodeBlock/Shiki having no ANSI rendering capability

## Solution
1. Backend: Replace strip-ansi with targeted removal of only VSCode shell
   integration sequences (OSC 633/133), preserving standard ANSI SGR codes
2. Frontend: Add new TerminalOutput component using ansi-to-html library
   that converts ANSI sequences to styled HTML spans
3. Map ANSI colors to VSCode terminal theme CSS variables for consistent
   theming across light/dark themes

## Testing
- Verified XSS prevention (escapeXML: true)
- Verified theme compatibility
- Added unit tests for both backend and frontend changes
- Updated existing tests to expect ANSI codes in output

Bundle size impact: ~3KB gzipped (ansi-to-html library)

Co-authored-by: Zman771 <605281+Zman771@users.noreply.github.com>
…7643938474473035449

fix: render ANSI escape codes in inline terminal output
@dosubot dosubot bot added size:L This PR changes 100-499 lines, ignoring generated files. Enhancement New feature or request labels Feb 10, 2026
@roomote
Copy link
Contributor

roomote bot commented Feb 10, 2026

Rooviewer Clock   See task

Found 1 issue to address before merging.

  • stripCursorSequences regex /\x1B\[su/g matches literal ESC[su instead of individual ESC[s and ESC[u cursor save/restore sequences -- should use a character class /\x1B\[[su]/g

Mention @roomote in a comment to request specific changes to this pull request or fix all unresolved issues.

private stripCursorSequences(text: string): string {
return text
.replace(/\x1B\[\d*[ABCDEFGHJ]/g, "") // Remove cursor movement: up, down, forward, back
.replace(/\x1B\[su/g, "") // Remove cursor position save/restore
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Bug: /\x1B\[su/g matches the literal 4-character sequence ESC[su, which is not a real ANSI sequence. Cursor save (ESC[s) and cursor restore (ESC[u) are two separate sequences. This regex will never match either one individually, so these cursor codes will pass through unstripped into the webview output. The fix is to use a character class so the regex matches either letter.

Suggested change
.replace(/\x1B\[su/g, "") // Remove cursor position save/restore
.replace(/\x1B\[[su]/g, "") // Remove cursor position save/restore

Fix it with Roo Code or mention @roomote and request a fix.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Enhancement New feature or request size:L This PR changes 100-499 lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[ENHANCEMENT] Inline terminal rendering parity with VSCode Terminal on Windows

1 participant