Skip to content

Conversation

@b3nw
Copy link

@b3nw b3nw commented Jan 16, 2026

Summary

  • Centralizes OSC 52 escape sequence handling in Clipboard.copy() so all clipboard operations work over SSH
  • Removes duplicate OSC 52 code from app.tsx, dialog.tsx, and session/index.tsx
  • Adds TTY check, JSDoc documentation, and GNU Screen support

Resolves anomalyco#2773

Changes

File Change
clipboard.ts +16 lines: writeOsc52() with JSDoc, TTY check, tmux/screen passthrough
app.tsx -10 lines: removed duplicate OSC 52 blocks
dialog.tsx -5 lines: removed duplicate OSC 52 block
session/index.tsx -5 lines: removed duplicate OSC 52 block

Testing

Verified locally:

  • ✅ Text selection copy (local terminal)
  • ✅ Copy last message (Ctrl+X Y)
  • ✅ Copy session transcript
  • ✅ Clipboard works over SSH
  • ✅ Clipboard works in tmux

Also submitted as anomalyco/opencode#8974

Greptile Summary

Centralizes OSC 52 escape sequence handling in Clipboard.copy() to enable clipboard operations over SSH for all clipboard operations in the TUI. The implementation adds a new writeOsc52() function with TTY detection, Base64 encoding, and DCS passthrough wrapping for tmux/screen.

Key changes:

  • Added writeOsc52() function in clipboard.ts with JSDoc, TTY check (process.stdout.isTTY), and automatic tmux/screen DCS passthrough detection
  • Removed 20 lines of duplicate OSC 52 code from app.tsx (2 locations), dialog.tsx, and session/index.tsx
  • All clipboard copy operations now benefit from SSH clipboard support

Issues found:

  • The DCS passthrough sequence uses the same tmux format for both tmux and GNU Screen, but Screen requires a different sequence without the "tmux;" prefix

Confidence Score: 4/5

  • Safe to merge after fixing the GNU Screen DCS passthrough sequence
  • The refactoring successfully centralizes OSC 52 handling and eliminates code duplication, but contains a logic bug where GNU Screen uses the wrong DCS passthrough format (tmux's format instead of Screen's)
  • Pay attention to clipboard.ts:19 - the GNU Screen passthrough needs correction

Important Files Changed

Filename Overview
packages/opencode/src/cli/cmd/tui/util/clipboard.ts Added centralized writeOsc52() function with TTY check, tmux/screen DCS passthrough wrapping
packages/opencode/src/cli/cmd/tui/app.tsx Removed duplicate OSC 52 code from two clipboard copy operations, now using centralized function
packages/opencode/src/cli/cmd/tui/ui/dialog.tsx Removed duplicate OSC 52 code from text selection copy, now using centralized function
packages/opencode/src/cli/cmd/tui/routes/session/index.tsx Removed duplicate OSC 52 code from message copy operation, now using centralized function

Sequence Diagram

sequenceDiagram
    participant User
    participant App as app.tsx/dialog.tsx/session
    participant Clipboard as Clipboard.copy()
    participant WriteOsc52 as writeOsc52()
    participant Terminal as Terminal Emulator
    participant OS as OS Clipboard

    User->>App: Select text & copy
    App->>Clipboard: Clipboard.copy(text)
    Clipboard->>WriteOsc52: writeOsc52(text)
    
    alt is TTY
        WriteOsc52->>WriteOsc52: Base64 encode text
        WriteOsc52->>WriteOsc52: Build OSC 52 sequence
        
        alt TMUX or STY env set
            WriteOsc52->>WriteOsc52: Wrap with DCS passthrough
        end
        
        WriteOsc52->>Terminal: Write escape sequence to stdout
        Terminal->>OS: Copy to local clipboard
    else not TTY
        WriteOsc52-->>Clipboard: Return (skip OSC 52)
    end
    
    Clipboard->>Clipboard: getCopyMethod()
    Clipboard->>OS: Platform-specific copy (osascript/wl-copy/xclip/etc)
Loading

seilk and others added 30 commits January 15, 2026 22:01
rekram1-node and others added 27 commits January 16, 2026 11:39
@b3nw
Copy link
Author

b3nw commented Jan 16, 2026

Closing in favor of a cleaner PR based on shuvcode's integration branch

@b3nw b3nw closed this Jan 16, 2026
Copy link

@greptile-apps greptile-apps bot left a comment

Choose a reason for hiding this comment

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

124 files reviewed, 1 comment

Edit Code Review Agent Settings | Greptile

const osc52 = `\x1b]52;c;${base64}\x07`
// tmux and screen require DCS passthrough wrapping
const passthrough = process.env["TMUX"] || process.env["STY"]
const sequence = passthrough ? `\x1bPtmux;\x1b${osc52}\x1b\\` : osc52
Copy link

Choose a reason for hiding this comment

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

logic: uses tmux DCS passthrough for both tmux and GNU Screen, but Screen requires \x1bP\x1b${osc52}\x1b\\ (without "tmux;")

Suggested change
const sequence = passthrough ? `\x1bPtmux;\x1b${osc52}\x1b\\` : osc52
const sequence = process.env["TMUX"] ? `\x1bPtmux;\x1b${osc52}\x1b\\` : process.env["STY"] ? `\x1bP\x1b${osc52}\x1b\\` : osc52
Prompt To Fix With AI
This is a comment left during a code review.
Path: packages/opencode/src/cli/cmd/tui/util/clipboard.ts
Line: 19:19

Comment:
**logic:** uses tmux DCS passthrough for both tmux and GNU Screen, but Screen requires `\x1bP\x1b${osc52}\x1b\\` (without "tmux;")

```suggestion
  const sequence = process.env["TMUX"] ? `\x1bPtmux;\x1b${osc52}\x1b\\` : process.env["STY"] ? `\x1bP\x1b${osc52}\x1b\\` : osc52
```

How can I resolve this? If you propose a fix, please make it concise.

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

clipboard copy not works in remote SSH console.