Files
orca/src/main/runtime
Brennan BensonandJinwoo-H 1ba71d2cee fix(mobile): background-mount never-mounted terminals on subscribe so they don't render blank (STA-1840) (#8811)
* fix(mobile): background-mount never-mounted terminals on subscribe so they don't render blank (STA-1840)

A mobile terminal.subscribe to a tab the desktop never mounted this session —
a workspace the desktop isn't currently showing, a cold-activation-deferred tab
(#8597), or a cold-parked tab — has no attached PTY, so the runtime has no
headless emulator and the initial snapshot is empty. The mobile terminal then
renders blank (repro: on the phone, scroll to an old workspace whose terminals
the desktop unmounted; they stay blank).

When a mobile subscribe hits an empty snapshot (or resolves no PTY), the runtime
now asks the renderer to background-mount that tab so the PTY attaches and the
live data stream — already subscribed on that path — delivers its output.

A never-mounted workspace has no renderer-graph leaf, so its terminals are
surfaced to mobile via synthetic pty:<ptyId> handles that carry no real UI
tabId. The runtime passes the ptyId through the mount request and the renderer
resolves the owning tab from the persisted tab model (resolveTerminalTabIdForPtyId),
falling back to a whole-worktree background mount if it cannot. The request is
idempotent for already-mounted tabs and never unmounts a live pane, so the worst
case is the same blank as before — no regression.

Validated on an iOS simulator with a two-workspace desktop: opening the
workspace the desktop was not showing rendered a fully blank terminal without
the fix and the live shell prompt with it.

Tests: runtime mount-request gating (real-tab / pty-form / no-ptyId / unknown),
subscribe-handler empty-snapshot-vs-content, and the ptyId->tabId resolver; all
608 RPC method tests pass.

* test(mobile): mock onRequestTerminalTabMount in useIpcEvents tests (fixes CI for #8811)

* fix(mobile): harden blank terminal recovery mounts

* perf(mobile): avoid redundant terminal recovery mounts

* fix(mobile): ignore stale terminal mount requests

* fix(mobile): skip recovery mounts for closed streams

* fix(mobile): reject ambiguous terminal mount ownership

* fix(mobile): preserve terminal handle through recovery mount

* fix(mobile): recover legacy terminal history safely

---------

Co-authored-by: Jinwoo-H <jinwoo0825@gmail.com>
2026-07-15 19:14:22 -07:00
..