Commit Graph
274 Commits
Author SHA1 Message Date
Jinjing 3a3e33f14b The --sandbox flag (or terminal sandboxing) in Google Antigravity is a (#8017)
Here is a summary of how the sandbox behaves on your macOS system:

### ⚙️ How it Works
When `--sandbox` is enabled (either via the launch flag or the `enableTerminalSandbox` setting in your `settings.json`), terminal commands run inside a lightweight containment boundary:
- **macOS Native Isolation**: It utilizes macOS's native `sandbox-exec` utility to restrict system calls, network sockets, and directory access.
- **Secure File Boundaries**: File system writes are locked down to designated safe zones (such as your designated workspace or scratch directory). Access to critical system paths, private user data, and external network resources is restricted.

---

### 🛡️ Active Permissions for this Session
In this current session, the permission model is configured as follows:

| Action / Resource | Permission Status | Details / Paths |
| :--- | :--- | :--- |
| **Command Execution** | ✅ **Allowed** | Terminal command execution is enabled. |
| **File Reads (Allowed)** | ✅ **Allowed** | `/scratch`, `/browser_recordings`, `/html_artifacts`, `/knowledge`, `/worktrees`, `/skills`, `/builtin` |
| **File Writes (Allowed)**| ✅ **Allowed** | `/scratch`, `/browser_recordings`, `/html_artifacts`, `/knowledge`, `/worktrees` |
| **Sensitive Files** | ⚠️ **Ask** | `.env`, `.npmrc`, `.vscode`, `.git-credentials`, etc. |
| **Root/App Settings** | 🚫 **Denied** | Direct modifications to `/config` and main `.gemini` configurations |

---

### 🔧 Configuration and Management

* **Persistent Settings**:
  To enable sandboxing by default for all future sessions, configure the `enableTerminalSandbox` setting in your `~/.gemini/antigravity-cli/settings.json`:
  ```json
  {
    "enableTerminalSandbox": true
  }
  ```

* **Dynamic Adjustments**:
  Within an active CLI (`agy`) session, you can run the `/permissions` slash command to view or modify your autonomy and sandboxing levels on the fly.

> [!NOTE]
> Running in sandbox mode provides an excellent balance of autonomy and security, allowing me to execute build commands, run test scripts, and manage project files safely without risk to your primary host environment.

Please let me know if you would like me to set up a new project workspace or run any specific tasks within this session!
2026-07-09 22:01:22 -07:00
Jinjing 44d5ed0439 1.4.131 rc2 release prep (#8020)
* Support WSL Codex settings promotion and harden config write-back

- Enable settings promotion for WSL runtimes using per-distro baselines.
- Create parent directories if missing to prevent promotion ENOENTs.
- Keep restrictive permissions (0600) and follow symlinks on promote.
- Respect CRLF line endings when inserting keys into CRLF config files.
- Skip redundant baseline file writes when settings are unchanged.
- Include the release scan report for the 1.4.131-rc2 prep.

* Refactor sleeping agent wake flow and fetch rate limits via backend

- Background-mount only targeted terminal tabs during passive wake to
  prevent spawning unnecessary PTYs for unvisited tabs.
- Latch edge-triggered wake requests that arrive mid-hibernation and
  track active claims to prevent double-resuming a provider session.
- Query the ChatGPT wham usage backend API directly with fetch for
  rate limits, avoiding launching Codex or WSL login shells.
- Asynchronously probe and serialize WSL auth files with timeouts to
  prevent synchronous I/O from stalling Electron's main process.
- Fix config promotion edge cases such as missing parent directories,
  dangling symlinks, and atomic write permission widening.

* Support WSL dotfile-symlink write-back and lengthen redeem timeout

- Preserve symlinked Codex config on WSL by writing through the
  existing file instead of atomic-rename, since \\wsl$ symlink
  metadata isn't reliably detected and rename would clobber the link.
- Tighten new ~/.codex directory creation to 0700 (holds auth.json).
- Give explicit reset-credit redemption a 30s backend timeout instead
  of the 10s background-poll default, since it's user-triggered.
- Read sleeping-agent session state from the worktree's actual
  execution-host partition instead of always the local one, so the
  headless-wake check works correctly for SSH-hosted worktrees.
- Isolate serve-sim watcher tests from the real $TMPDIR/serve-sim
  state file to avoid leaking unrelated events.
2026-07-09 21:54:22 -07:00
Jinjing 3a7eb8f312 fix(mobile): drop smart-dash write-back recovery that kills iOS dictation (#8008)
The longer-hyphen recovery path (#5222) reconstructed runs by writing a
value that differed from the native field text. After #7933 stores raw
field text and normalizes only on send/PTY, that recovery is unreachable
and any write-back would reintroduce dictation kill. Map each smart dash
to exactly "--" with a single-arg normalizer.
2026-07-09 20:38:17 -07:00
Jinjing 43f639ddda Consolidate mobile source control into a single tabbed hub (#7923)
* Consolidate mobile source control into a single tabbed hub

Unify the changes list, pull request details, and commit history into
a single multi-segment panel. This improves navigation and state sharing
across different lenses of a worktree's source control.

- Add a segmented control to switch between Changes, PR, and History
- Introduce a persistent branch status card with an integrated PR chip
- Redirect standalone PR and history routes to the new unified hub
- Extract reusable UI and logic for the history list and PR summary

* Keep mobile source control tabs mounted to preserve view state

* Keep PR and History segments mounted (using display: 'none' when hidden) to preserve fetch, scroll, and expand states during tab switches.
* Decouple the History list from blocking on Git status loading.
* Support deep linking directly into the history tab of the main panel instead of using a standalone route.
* Enable retrying failed loads by reviving the transport loop if parked.
* Fix PR chip accessibility label and comment check.

* Optimize and integrate mobile PR view within source control hub

- Lazy-load heavy PR comments and descriptions (Phase 2) only when the
  PR tab is active, using fast metadata (Phase 1) for the branch chip.
- Unmount the PR body when inactive to avoid unnecessary comment tree
  re-renders and preserve WebView resources during commit text editing.
- Implement soft-refresh on HEAD advancement to keep the ready UI
  visible while re-fetching checks post-commit.
- Display the "Aborting..." label only when a merge or rebase abort
  is actively in flight.
- Memoize the git history list and skip branch identity RPCs when
  gating the dock icon.

* Improve mobile git views and concurrent rendering safety

- Pass the `origin` parameter through history and PR redirect routes.
- Move source control panel ref updates to `useEffect` to prevent side
  effects during concurrent renders.
- Resolve commit file changes to empty if disconnected to avoid a stuck
  loading spinner.
- Standardize PR sidebar header button styling and accessibility labels.

* Resolve PR repo probe without active branch to avoid forever spinner

Previously, checking if a repository is a GitHub remote required an
active branch. In a detached HEAD or mid-rebase state (where the branch
is null), the probe never resolved, leaving the PR panel on a forever
spinner.

Decouple the repository probe from the branch presence so the panel
can correctly display the "Current branch unavailable" state. Also,
hide the PR status chip when no branch is active to avoid a spinner
on the chip.
2026-07-09 19:23:36 -07:00
Jinwoo HongandOrca 9c111fd7aa mobile: per-host connection log screen with copy-diagnostics (#7984)
The rpc-client has always emitted a detailed connection lifecycle log
(dials, timeouts, close codes, handshake steps, retries) via onLog, but
only the pairing screen wired it up — for long-lived host connections
everything went to console.log, invisible to users. Debugging reports
like #7824/#6928 meant asking reporters for facts the app already knew.

- connection-log-buffer: bounded (200/host) module-level ring buffer with
  referentially-stable snapshots for useSyncExternalStore; survives
  client swaps and provider remounts.
- client-context: wire onLog for every shared host client.
- connection-log screen: live per-host log (reuses the pairing
  ConnectionLog component), host picker, and a Copy Diagnostics button
  that bundles app/platform versions, endpoint (flagged if Tailscale),
  state, attempt count, last-connected, and the event log into one
  shareable blob.
- troubleshoot: 'View connection log' entry point.

Co-authored-by: Orca <help@stably.ai>
2026-07-09 16:20:07 -07:00
Jinwoo HongandOrca 73f1bbfc94 mobile: recover from wedged Tailscale tunnels and say 'check Tailscale' when it's the likely culprit (#7980)
A wedged Tailscale tunnel (known iOS failure mode) produces no AppState
or network-type transition, so no revival nudge ever fires and the
reconnect loop parked permanently at its give-up cap — users had to
toggle Tailscale off/on just to force a transition (#7824).

- rpc-client: past the give-up cap, drop to a 90s trickle dial instead
  of parking so the session self-heals once the tunnel recovers.
- host screen: nudge the shared client on focus so opening the host
  retries immediately instead of waiting out a backoff/trickle timer.
- connection-health: warning/unreachable verdicts on 100.64/10 or
  *.ts.net endpoints now carry a 'check Tailscale' hint, shown on the
  home host list and the in-session status line after ~3 failed
  attempts.
- troubleshoot: 'Cannot reach <tailnet-ip>' now says to check
  Tailscale, adds a dedicated Tailscale section, and stops telling
  Tailscale users to disable their VPN (that advice killed their only
  route to the host); sections extracted to
  troubleshoot-common-issues.tsx to stay under the max-lines cap.

Co-authored-by: Orca <help@stably.ai>
2026-07-09 15:56:25 -07:00
Jinjing 6fb3036464 Fix iOS native keyboard dictation in mobile terminal inputs (#7933) 2026-07-09 05:02:39 -07:00
Brennan BensonandOrca d1cc78d5c5 fix(mobile): bump Android versionCode to 6 for the 0.0.25 release (#7907)
Co-authored-by: Orca <help@stably.ai>
2026-07-09 00:29:42 -07:00
Jinjing 7f3e851696 Add external link button to open PR in mobile browser (#7879)
Introduce an external link action in the header of the Mobile PR View
Panel. This provides a persistent and easily accessible shortcut to open the
current pull request's canonical URL in the system browser.
2026-07-08 20:55:59 -07:00
Brennan BensonandOrca 47389990a5 fix(mobile): surface disconnected source-control states + keep the mobile WS fallback port stable (STA-1511) (#7855)
Co-authored-by: Orca <help@stably.ai>
2026-07-08 18:28:59 -07:00
60037d60ab feat(mobile): add explicit keyboard dismiss control to terminal command dock (#5917)
* feat(mobile): add explicit keyboard dismiss control to terminal command dock

Add a fixed Hide control at the left of the terminal command dock accessory
bar whenever the software keyboard is open (keyboardHeight > 0). Tapping it
clears any pending live-input focus timer, blurs the live and buffered command
inputs, and dismisses the keyboard without sending bytes, switching input mode,
or clearing typed text.

The dismiss behavior lives in a dedicated, unit-tested terminal-keyboard-dismiss
module rather than the customizable accessory-key path, so the escape hatch
cannot be hidden by user shortcut customization. Available on every platform
where the IME covers the app (iOS and Android).

* review: harden keyboard dismiss control per adversarial review

- document the load-bearing clear-before-blur order in dismissTerminalKeyboard
- cover the both-handles-missing case in unit tests (5/5)
- move the #5106 first-tap comment onto the accessory ScrollView and add a
  why-comment for the fixed Hide control
- add accessibilityRole=button and hitSlop to the Hide control for a larger,
  semantically-correct touch target

* fix(mobile): harden hide button visibility and scroll layout

* refactor(mobile): use stacked keyboard+chevron glyph for dismiss control

Replace the icon+'Hide' text with the iOS-native dismiss glyph (keyboard
with a chevron-down beneath it). Narrower in the accessory row, removes the
icon/word redundancy, and reads as distinct from the >> input-mode toggle.
Accessibility label/hint/role unchanged.

* fix(mobile): align keyboard dismiss accessory height

* test(mobile): align vitest transform with Vite 8

---------

Co-authored-by: Wolfgang Schoenberger <221313372+wolfiesch@users.noreply.github.com>
Co-authored-by: Jinwoo-H <jinwoo0825@gmail.com>
2026-07-08 17:18:16 -07:00
Brennan BensonandOrca 46fe1b5799 Prepare mobile 0.0.25 (#7751)
Co-authored-by: Orca <help@stably.ai>
2026-07-07 16:05:18 -07:00
Neil 54c4959830 perf(mobile): cap the scheduled-notification map + tap-dedup set (#7646)
scheduledNotificationsByHostAndNotificationId (mobile-notifications.ts)
retained one entry per scheduled desktop notification. The key embeds
notificationId, which carries a per-completion timestamp
(buildAgentNotificationId), so every agent-task-complete inserts a new,
never-reused key. Entries are removed only when the desktop sends a
matching dismiss — which a remote mobile user (not sitting at the
desktop) frequently never receives — so the module-level map grew for
the app's whole lifetime. Small per entry, but genuinely unbounded.

Fix: bound the map to the 256 most-recent SETTLED entries (never evict
one mid-schedule). A settled entry only retains a small identifier used
for later programmatic dismissal, which is unnecessary for long-past
completions, so eviction has no user-visible effect.

Also FIFO-cap RootLayout's handledNotificationIdsRef tap-dedup Set
(RootLayout never unmounts, so it otherwise grew one id per tapped
notification forever).

Test (red->green): with the cap at 1, scheduling a second notification
evicts the first, so a later dismiss for the evicted id is a no-op while
the retained one still dismisses; without the cap the old entry survives.
2026-07-06 21:28:09 -07:00
Brennan BensonandOrca 9a3bf1293c Mobile file tree follow-ups: reconnect no-blank + old-desktop files.list fallback (#7599)
Co-authored-by: Orca <help@stably.ai>
2026-07-06 17:13:21 -07:00
Brennan BensonandOrca 99ae2dc90f Show full workspace file tree on mobile (#7289)
Co-authored-by: Orca <help@stably.ai>
2026-07-06 15:41:51 -07:00
NeilandOrca e33b2006f4 Remove stale max-lines lint disables from files under the limit (#7548)
110 files carried an eslint/oxlint-disable max-lines directive but are
already under the default max-lines budget (300 .ts / 400 .tsx / 600 .mjs
/ 800 test), so the suppression is dead. Removing it restores real
max-lines coverage on these files with zero behavior change.

Each removed directive had max-lines as its only rule; verified via a
full oxlint run (0 max-lines violations, 0 new errors). Diff is pure
deletions (200 lines, 0 additions) — no code touched.

Co-authored-by: Orca <help@stably.ai>
2026-07-06 02:12:32 -07:00
JinjingandOrca 3c963dd285 Prepare mobile 0.0.24 (#7546)
Bump marketing version 0.0.22 -> 0.0.24 and Android versionCode 4 -> 5.

The 0.0.22 base was never committed after prior releases, so the Jul 6
builds carrying the show-all-worktrees fix (#7500) regressed below the
0.0.23 already on TestFlight (iOS) and collided with the existing
0.0.22/versionCode 4 APK (Android, no upgrade signal). Committing the
bump makes app.json authoritative again so 0.0.24 supersedes both.

Co-authored-by: Orca <help@stably.ai>
2026-07-06 01:39:40 -07:00
Neil ce687221d3 lint(unicorn): enable prefer-number-properties, prefer-array-find, prefer-array-index-of (#7516)
Enable three unicorn rules — one correctness, two performance — and fix every
existing violation repo-wide so the rules pass as errors.

prefer-number-properties (76 sites)
- parseInt/parseFloat/NaN -> Number.* : safe aliases (autofixed).
- isNaN -> Number.isNaN (12 sites, hand-converted): global isNaN coerces its
  argument, Number.isNaN does not. Verified every call site already passes a
  number (Number.parseInt results, number-typed fields, Date.getTime()), so the
  conversion is behavior-preserving today and guards against a future non-numeric
  argument silently coercing.

prefer-array-find (26 sites)
- .filter(pred)[0] -> .find(pred); .filter(pred).at(-1) / .pop() -> .findLast(pred).
  Drops the intermediate array and short-circuits.

prefer-array-index-of (5 sites)
- .findIndex(x => x === v) -> .indexOf(v).

Verified: typecheck (node/cli/web) clean, 53 affected suites pass (1679 tests),
oxlint clean repo-wide. mobile/ uses findLast safely (already ships ES2023
.toReversed()); config scripts and e2e helpers run on Node 24.
2026-07-05 23:56:37 -07:00
JinjingandOrca 430d4b9482 Show all worktrees across all hosts on mobile (#7500)
* Show all worktrees across all hosts on mobile

Avoid honoring desktop's host-filtering settings since mobile lacks the
UI to manage or unhide them. This prevents worktrees from being silently
hidden under certain host scopes.

Additionally, this removes worktree filtering based on repo metadata, which
previously caused worktrees to vanish when same-named repos on different
hosts collapsed to a single ID.

* fix(daemon): preserve promisify.custom type through wrapChildProcessApi

The windows-hidden-console-children test (from #7499, admin-merged with a
failing verify) failed tsgo: promisify(wrapped) resolved to its zero-arg
overload because the wrapper erased its argument to a bare variadic function
and the fake never statically carried promisify.custom. Preserve the wrapped
type via a generic overload (accurate: the wrapper copies the call signature
and symbols verbatim) and build the fake as a real CustomPromisify, so
promisify routes through the custom overload as it does in production.

Co-authored-by: Orca <help@stably.ai>

---------

Co-authored-by: Orca <help@stably.ai>
2026-07-05 23:10:48 -07:00
Kaynan Sampaio de Camargo 12e60054b0 fix(mobile): dismiss keyboard when opening repo/agent pickers in Create Workspace (#7365) 2026-07-05 21:02:43 -07:00
Jinjing e7d1fa4a21 Disable auto-merge for unstable GitHub PRs (#7415)
Prevent enabling auto-merge when a PR is in an UNSTABLE merge state.
GitHub auto-merge mutations reject UNSTABLE PRs directly instead of
allowing them to wait, so we should suppress the option.
2026-07-05 11:05:58 -07:00
Jinjing bdb6d144c3 Pin the new tab button outside the tab scroll view (#7292)
Move the "New tab" button out of ScrollView so that it remains visible
and reachable regardless of how far the tabs have been scrolled.
2026-07-03 19:38:24 -07:00
Brennan BensonandOrca 95caf2ee9d fix(mobile): match diff review line height to desktop diff density (#7276)
Co-authored-by: Orca <help@stably.ai>
2026-07-03 17:34:44 -07:00
d9e0b9e759 fix(mobile): avoid SF Mono fallback on iOS terminal (#6761)
* fix(mobile): avoid SF Mono fallback on iOS terminal

* test(mobile): cover touch iPadOS terminal font fallback

* refactor(mobile): share terminal font fallback tail across platforms

Dedup the identical fallback chain that the iOS/non-iOS branches each
repeated so the two platforms can only differ in the lead family and
cannot silently drift. Make the regression tests behavioral: assert the
resolved chain always terminates in the generic monospace (the real iOS
bug) and that both platforms share an identical tail.

Co-authored-by: Orca <help@stably.ai>

* test(mobile): anchor font-block extraction on font markers only

The VM-slice end boundary was an unrelated text-scale comment; re-anchor
it on the terminalFontFamily declaration so edits below the font block
cannot break the extraction.

Co-authored-by: Orca <help@stably.ai>

* chore(mobile): bump terminal-webview-html max-lines ratchet to match file size

The iOS-safe font selection block adds a few code lines to
terminal-webview-html.ts, pushing it to 1784. Bump the grandfathered
per-file ratchet to match, consistent with prior ratchet bumps.

Co-authored-by: Orca <help@stably.ai>

---------

Co-authored-by: Neil <4138956+nwparker@users.noreply.github.com>
Co-authored-by: Orca <help@stably.ai>
2026-07-03 17:11:24 -07:00
e8c2b79a93 Fix mobile live input keyboard and Korean IME (#7273)
* feat: 모바일 터미널 한글 미러 스텝 순수 모델 추가

* feat: 미러 델타 순서 보장용 send 체인 추가

* fix: 모바일 터미널 한글 입력을 미러 모델로 전환

* fix: 탭 상태 지연 중 한글 조합 상태 소실 방지

* fix: 미러 가드와 send 체인 리뷰 지적사항 반영

탭 상태 지연으로 활성 탭 타입이 일시적으로 null이 될 때 runMirrorStep의 stale-handle 가드가 조합 중 음절을 버리지 않도록 pending-clear 효과와 동일한 null 허용 패턴 적용. 테스트 하네스가 ref와 prop을 동일 소스에서 파생하도록 결합해 실제 경로의 lag 프레임을 검증. queueTerminalLiveMirrorSend의 previousSend await를 catch로 보호.

* refactor(mobile): drop dead queueTerminalLivePendingFlush orphaned by the mirror model

The mirror model migrated all live-input sends to queueTerminalLiveMirrorSend,
leaving queueTerminalLivePendingFlush referenced only by its own tests. Remove
the dead function and its three tests.

Co-authored-by: Orca <help@stably.ai>

* fix(mobile): expose live terminal keyboard target

Co-authored-by: Orca <help@stably.ai>

* fix(mobile): refocus live keyboard after dismissal

Co-authored-by: Orca <help@stably.ai>

---------

Co-authored-by: realitsyourman <wongil@demodev.io>
Co-authored-by: Neil <4138956+nwparker@users.noreply.github.com>
Co-authored-by: Orca <help@stably.ai>
2026-07-03 16:47:59 -07:00
Jinwoo HongandOrca 25896f2cdb fix(mobile): keep Android release versionCode committed (#7271)
Co-authored-by: Orca <help@stably.ai>
2026-07-03 15:26:11 -07:00
Brennan BensonandOrca f4790e9fac Fix blank mobile terminal on Android devices with outdated WebViews or blocked CDN (#7186)
* fix(mobile): bundle terminal engine and show load errors instead of a blank pane

The mobile terminal WebView loaded xterm.js from cdn.jsdelivr.net at
runtime; old WebViews (< Chrome 85) fail to parse the modern bundle and
blocked-CDN networks fail to fetch it, and the resulting error was
silently dropped, leaving the pane permanently blank (#7030).

Bundle the engine into the app via exact-pinned npm deps + a postinstall
esbuild step (chrome74 target, guarded WeakRef/structuredClone/
replaceChildren shims) emitting a gitignored generated module, inline it
into the terminal document, and surface fatal engine failures as a
visible overlay with diagnostics and a Reload wired into the existing
resubscribe path. Non-fatal errors log without covering a live terminal.

Co-authored-by: Orca <help@stably.ai>

* fix(mobile): add a native watchdog so a dead terminal document can't stay silently blank

CodeRabbit round: if the webview document dies before the glue can post
anything (or the RN message bridge never comes up), no error message and
no native handler fires. Arm a 15s foreground-gated watchdog per document
generation that paints the fatal overlay when web-ready never arrives;
first fatal diagnostics win over later cascades. Extract the watchdog and
the public contract types to keep TerminalWebView under the line cap, and
document the SVG xmlns percent-encoding transform.

Co-authored-by: Orca <help@stably.ai>

* test(mobile): unmount TerminalWebView renderers so watchdog timers can't leak across tests

Co-authored-by: Orca <help@stably.ai>

---------

Co-authored-by: Orca <help@stably.ai>
2026-07-03 15:22:00 -07:00
Brennan BensonandOrca d8921a22ad Bump mobile app.json to 0.0.22 (#7261)
Co-authored-by: Orca <help@stably.ai>
2026-07-03 13:42:09 -07:00
Siddiqui Qamar f0278c116e fix(mobile): preserve terminal input mode on reentry (#7129)
Fixes #6972.\n\nPreserves mobile terminal buffered/live input mode across Android terminal re-entry and session refreshes. Includes follow-up hardening for pre-hydration preference edits and failed storage reads.
2026-07-02 23:22:30 -07:00
Brennan BensonandOrca c06507ee30 Open terminal file links on mobile (#7134)
Co-authored-by: Orca <help@stably.ai>
2026-07-02 18:17:47 -07:00
Jinjing e3f99a7472 Bump mobile app.json to 0.0.20 (#7100) 2026-07-02 02:42:52 -07:00
WONGILandJinjing 4f0a141951 Fix mobile terminal Korean IME composition on Android (#7011)
* Fix Korean IME composition by deferring live terminal preedit

The mobile terminal capture field previously sent and cleared every TextInput change, which can break Hangul composition on Android keyboards. Introduce a small commit model and extracted live-input hook so composed text is flushed deliberately while ASCII remains immediate.

Constraint: React Native TextInput has no portable composition event for this path; the fix uses a bounded commit delay for likely IME text.

Rejected: Native-module IME integration | unnecessary for the confirmed JS dispatch/clear failure and higher maintenance risk.

Confidence: high

Scope-risk: moderate

Directive: Keep terminal.send payload shape and buffered command input unchanged; do not claim physical Samsung Keyboard QA without device evidence.

Tested: cd mobile && pnpm exec vitest run src/terminal/terminal-live-text-commit.test.ts src/terminal/terminal-live-input.test.ts src/terminal/terminal-text-input-normalization.test.ts src/terminal/terminal-keyboard-type.test.ts --reporter=verbose

Tested: cd mobile && pnpm exec tsc --noEmit

Tested: cd mobile && pnpm exec oxlint src/terminal/terminal-live-text-commit.ts src/terminal/terminal-live-text-commit.test.ts src/terminal/use-terminal-live-input-commit.ts app/h/[hostId]/session/[worktreeId].tsx

Not-tested: Physical Galaxy Fold7/Samsung Keyboard and Android emulator/Gboard QA were unavailable; device probes recorded no attached Android device.

* Preserve pending Korean IME text before mobile accessory controls

Accessory keys share the same pending live-input commit gate as TextInput keypress and submit paths, so control bytes cannot race ahead of composed Hangul.

Constraint: React Native mobile input does not expose portable composition events for Samsung/Gboard IME paths.

Rejected: Let accessory buttons keep sending directly | Direct sends can drop pending Hangul before Tab/Esc/Enter/Backspace reaches the PTY.

Confidence: high

Scope-risk: narrow

Directive: Keep all terminal control-byte paths behind the pending live-input flush/local-edit decision before sending to the PTY.

Tested: pnpm --dir mobile test; pnpm --dir mobile lint; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile exec oxfmt --check src/terminal/terminal-live-text-commit.ts src/terminal/terminal-live-text-commit.test.ts src/terminal/use-terminal-live-input-commit.ts src/terminal/use-terminal-live-accessory-input-commit.ts app/h/[hostId]/session/[worktreeId].tsx; git diff --cached --check

Not-tested: Physical Galaxy Fold7 Samsung keyboard manual QA is still external-device only.

* Prevent stale IME timer flushes after mobile terminal teardown

Pending live-input timers now clear on hook unmount, and accessory Delete documents why it stays local without trimming pending IME text.

Constraint: React Native TextInput lacks a portable composition lifecycle, so pending IME text is guarded by a bounded timer that must not survive screen teardown.

Rejected: Use clearPendingLiveInputCommit during unmount | it would also touch React state/native props during teardown when only timer/ref cleanup is required.

Confidence: high

Scope-risk: narrow

Directive: Any delayed terminal input commit must have an owner-lifecycle cleanup path before sending to the PTY.

Tested: pnpm --dir mobile test; pnpm --dir mobile lint; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile exec vitest run src/terminal/terminal-live-text-commit.test.ts --reporter=verbose; pnpm --dir mobile exec oxfmt --check src/terminal/terminal-live-text-commit.ts src/terminal/use-terminal-live-input-commit.ts; git diff --check

Not-tested: Physical Galaxy Fold7 Samsung keyboard manual QA remains unavailable in this environment.

* Use semantic accessory edits for mobile IME commits

Accessory Backspace/Delete now carry semantic local-edit intent from built-in keys instead of inferring intent from raw bytes, and submit handling is reconnected to the pure submit-sequence model.

Constraint: Custom terminal accessory keys may produce the same bytes as built-ins but should still flush pending IME text before sending rather than being silently treated as hidden-input edits.

Rejected: Classify local accessory edits by raw bytes | That couples future custom controls to current built-in byte encodings.

Confidence: high

Scope-risk: narrow

Directive: Keep semantic input intent separate from terminal byte payloads when pending IME text is present.

Tested: pnpm --dir mobile test; pnpm --dir mobile lint; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile exec oxfmt --check src/terminal/terminal-live-text-commit.ts src/terminal/terminal-live-text-commit.test.ts src/terminal/use-terminal-live-input-commit.ts src/terminal/use-terminal-live-accessory-input-commit.ts app/h/[hostId]/session/[worktreeId].tsx; git diff --check

Not-tested: Physical Galaxy Fold7 Samsung keyboard manual QA remains unavailable in this environment.

* Respect IME flush failures before control input

Propagate terminal.send success from pending Korean IME text before sending Enter, Tab, or accessory bytes, while keeping custom no-pending accessory bytes on the original direct path.

Constraint: PR #7011 review required follow-up control bytes only after the pending composed text send actually succeeds.

Rejected: Treating send invocation as success | It can still reject or no-op when RPC state changed.

Confidence: high

Scope-risk: narrow

Directive: Keep pending IME flush paths async-success-aware before adding new terminal control inputs.

Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; pnpm --dir mobile exec oxfmt --check changed files; targeted no-excuse clean for mobile/src/terminal changed files.

Not-tested: Physical Galaxy Fold7 Samsung keyboard; full session file no-excuse audit still reports pre-existing unrelated violations.

* Serialize mobile IME flushes before live controls

Treat terminal.send as successful only when the RPC response is ok and the runtime send result is accepted, then route all live-input control sends through a shared in-flight pending-flush barrier.

Constraint: PR #7011 review found that resolved RPC promises and per-call sequencing were not enough to prove pending Hangul text reached the PTY before follow-up controls.

Rejected: Only awaiting each flush-then-send call | Repeatable accessory keys and no-pending sends can arrive while the first flush is still in flight.

Confidence: high

Scope-risk: moderate

Directive: Keep future mobile terminal control paths behind the pending-flush barrier whenever IME text may be in flight.

Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; pnpm --dir mobile exec oxfmt --check changed files; no-excuse clean for terminal changed files.

Not-tested: Physical Galaxy Fold7 Samsung keyboard; full session file no-excuse audit still reports pre-existing unrelated violations.

* Queue current IME snapshots behind active flushes

Drain the pending snapshot captured by a control action after any already-active terminal send, and make accessory commit handling explicit so raw fallback is not encoded as an inverted boolean.

Constraint: Architecture review found the previous single-slot barrier could wait for an older flush while skipping newly pending Hangul text.

Rejected: Reusing the prior in-flight promise as the current flush result | It proves only an older snapshot, not the current pending buffer.

Confidence: high

Scope-risk: narrow

Directive: New mobile terminal control paths must distinguish allow-raw, handled, and suppress-raw outcomes explicitly.

Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; pnpm --dir mobile exec oxfmt --check changed files; no-excuse clean for terminal changed files.

Not-tested: Physical Galaxy Fold7 Samsung keyboard; full session file no-excuse audit still reports pre-existing unrelated violations.

* Preserve accessory raw-send terminal targets

Capture the terminal handle at accessory keypress time and suppress raw fallback if the active live terminal changes while waiting for pending IME flushes.

Constraint: Independent review found raw accessory bytes could retarget to a different terminal after an async IME flush barrier.

Rejected: Re-reading activeHandleRef as the send target after await | It can point at a different terminal than the keypress belonged to.

Confidence: high

Scope-risk: narrow

Directive: Raw accessory fallback must use the keypress-time target and revalidate it after any await.

Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; pnpm --dir mobile exec oxfmt --check changed files; no-excuse clean for terminal changed files.

Not-tested: Physical Galaxy Fold7 Samsung keyboard; full session file no-excuse audit still reports pre-existing unrelated violations.

* Document accessory flush barrier intent

Make the non-obvious raw accessory wait/suppress behavior explicit so future changes preserve IME-before-control ordering.

Constraint: CodeRabbit requested a why-comment for the send-now accessory branch.

Rejected: Leaving the barrier semantics implicit | The branch can otherwise look like unnecessary async defensive code.

Confidence: high

Scope-risk: narrow

Directive: Keep comments focused on why raw accessory bytes wait behind IME flushes.

Tested: targeted terminal vitest suite; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; oxfmt check for changed file.

Not-tested: Physical Galaxy Fold7 Samsung keyboard.

* Preserve buffered accessory raw sends

Keep the stale-handle guard focused on the captured active terminal instead of live-input opt-in state, so buffered mode keeps existing accessory key behavior while async live-input waits still cannot retarget to another terminal.

Constraint: Buffered command input behavior must remain unchanged while fixing mobile Korean IME live input ordering.
Rejected: Requiring live-input enabled handles for raw accessory fallback | suppresses valid buffered-mode accessory sends.
Confidence: high
Scope-risk: narrow
Directive: Do not use live-input opt-in state as terminal liveness for raw accessory sends; validate captured target, active terminal tab, connection, and client instead.
Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; oxfmt --check changed mobile terminal/session files; TypeScript no-excuse checker for changed terminal files.
Not-tested: Physical Galaxy Fold7 Samsung Keyboard manual QA and GitHub Actions jobs, blocked by unavailable device and upstream fork workflow approval.

* Keep Hangul IME text pending until explicit flush

Avoid timer-driven PTY writes for Hangul candidates so paused Korean composition cannot leak intermediate jamo, while preserving the bounded settle timer for non-Hangul IME text. Also keep disabled live-input accessory fallback behind any existing pending flush barrier.

Constraint: React Native TextInput does not expose a portable composition lifecycle on this mobile surface.
Rejected: Fixed 150ms auto-flush for Hangul | can emit ㅎ or 하 if the user pauses mid-composition.
Confidence: high
Scope-risk: narrow
Directive: Treat Hangul candidates as pending until submit/control/accessory flush; do not reintroduce idle timer commits for Hangul without device-level composition evidence.
Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; oxfmt --check changed mobile terminal/session files; TypeScript no-excuse checker for changed terminal files.
Not-tested: Physical Galaxy Fold7 Samsung Keyboard manual QA and GitHub Actions jobs, blocked by unavailable device and upstream fork workflow approval.

* Gate dictation toast on accepted live send

Honor the async live-input sender contract so the mobile UI reports dictation insertion only after terminal.send is accepted.

Constraint: sendLiveTerminalInput now returns false for stale, disconnected, oversized, or rejected terminal sends.
Rejected: Toasting immediately after dispatch | reports success for sends that never reached the PTY.
Confidence: high
Scope-risk: narrow
Directive: Treat live-input UI success as terminal.send acceptance, not request dispatch.
Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; oxfmt --check app/h/[hostId]/session/[worktreeId].tsx.
Not-tested: Physical Galaxy Fold7 Samsung Keyboard manual QA and GitHub Actions jobs, blocked by unavailable device and upstream fork workflow approval.

* Keep accessory edits on Hangul pending path

Make accessory local edits reuse the Hangul-aware defer policy so built-in Backspace/Delete cannot reintroduce timer-driven Hangul PTY writes.

Constraint: Hangul IME candidates must remain pending until explicit submit/control/accessory flush.
Rejected: Reusing the non-Hangul 150ms settle timer for accessory local edits | can leak pending Hangul after Backspace/Delete.
Confidence: high
Scope-risk: narrow
Directive: Any future pending-text reschedule must use getTerminalLiveDeferredTextDelayMs instead of a hardcoded timer.
Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; oxfmt --check changed mobile terminal/session files; TypeScript no-excuse checker for changed terminal files.
Not-tested: Physical Galaxy Fold7 Samsung Keyboard manual QA and GitHub Actions jobs, blocked by unavailable device and upstream fork workflow approval.

* Prove Hangul live-input hook ordering

Add a direct hook-level regression so Android Korean IME fixes are covered at the orchestration boundary, not only by lower-level helpers.

Constraint: React Native mobile TextInput lacks portable composition lifecycle events in this path.

Rejected: Relying only on helper tests | misses hook-level pending flush and submit ordering.

Confidence: high

Scope-risk: narrow

Directive: Keep Hangul candidates pending until an explicit terminal action flushes them.

Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; oxfmt --check changed mobile files; no-excuse on terminal modules

Not-tested: Physical Galaxy Fold Samsung Keyboard manual QA is not available in this environment.

* Keep accessory raw-send tests precise

Remove a duplicate raw-target assertion whose title implied disabled live-input behavior that is covered at the accessory commit boundary instead.

Constraint: Anti-slop cleanup must preserve existing Hangul/accessory behavior and stay within changed terminal tests.

Rejected: Keeping the duplicate disabled-input wording | it tests the same active-terminal predicate as the preceding case.

Confidence: high

Scope-risk: narrow

Directive: Test disabled live-input buffering in the accessory commit layer, not in the raw-target predicate helper.

Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; pnpm --dir mobile exec oxfmt --check changed mobile files; terminal no-excuse checker

Not-tested: Physical Galaxy Fold Samsung Keyboard manual QA is not available in this environment.

* Explain stale mobile terminal send gates

Document why async IME flush paths re-check terminal/client refs before sending raw bytes or reporting live-send success.

Constraint: CodeRabbit review requested short why comments for non-obvious stale-send safety gates.

Rejected: Leaving the gates undocumented | future edits could remove the stale-target suppression contract.

Confidence: high

Scope-risk: narrow

Directive: Keep async terminal sends guarded by current client, active handle, tab type, and connection state.

Tested: pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; pnpm --dir mobile exec oxfmt --check changed mobile files; terminal no-excuse checker

Not-tested: Physical Galaxy Fold Samsung Keyboard manual QA is not available in this environment.

* Run mobile IME hook tests through effects

Move the Hangul live-input hook regression from server rendering to react-test-renderer so effect cleanup and unmount timer cancellation are exercised.

Constraint: @testing-library/react-native imports React Native's Flow entry under this Vitest setup, so the narrow effect-running renderer is the compatible test surface.

Rejected: Keeping renderToString | it never runs useEffect cleanup and missed the pending timer cleanup path.

Rejected: Adding @testing-library/react-native directly | it failed before tests with React Native Flow syntax under the current Vitest transform.

Confidence: high

Scope-risk: narrow

Directive: Hook-level IME tests must use a renderer that runs effects when asserting pending flush cleanup.

Tested: vitest targeted terminal tests; pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; oxfmt --check changed mobile files; terminal no-excuse checker

Not-tested: Physical Galaxy Fold Samsung Keyboard manual QA is not available in this environment.

* Keep hook lifecycle tests quiet

Suppress only the react-test-renderer deprecation warning around the effect-running hook harness so real console errors still surface.

Constraint: CodeRabbit flagged React 19 renderer warning noise; @testing-library/react-native remains incompatible with the current Vitest/RN Flow transform path.

Rejected: Global console silencing | it would hide unrelated test failures.

Confidence: high

Scope-risk: narrow

Directive: Keep the renderer warning suppression scoped to this hook harness and pass all other console errors through.

Tested: vitest targeted terminal tests; pnpm --dir mobile test; pnpm --dir mobile exec tsc --noEmit; pnpm --dir mobile lint; oxfmt --check changed mobile files; terminal no-excuse checker

Not-tested: Physical Galaxy Fold Samsung Keyboard manual QA is not available in this environment.

* fix: flush pending mobile IME input before external sends

* fix: guard terminal command finished event dispatch

---------

Co-authored-by: Jinjing <6427696+AmethystLiang@users.noreply.github.com>
2026-07-02 02:31:19 -07:00
Brennan BensonandOrca b8d7bf0570 Bump mobile app version to 0.0.18 (#6941)
Co-authored-by: Orca <help@stably.ai>
2026-06-30 15:06:29 -07:00
Brennan BensonandOrca 77a7798156 Fix mobile Source Control primary action styling (#6918)
Co-authored-by: Orca <help@stably.ai>
2026-06-30 11:26:20 -07:00
JinjingandOrca f6db7897d7 fix(mobile): import Buffer from 'buffer', not 'node:buffer'
The oxlint 1.71 upgrade (#6841) autofixed these imports to the node:
protocol, which Metro can't resolve in a React Native bundle, breaking
the Android release build ("Unable to resolve module node:buffer").
Revert to the npm 'buffer' polyfill and disable prefer-node-protocol for
the mobile package so the autofix can't reintroduce the regression.

Co-authored-by: Orca <help@stably.ai>
2026-06-30 01:15:56 -07:00
Neil f9e18910ae chore(lint): adopt unicorn/prefer-import-meta-properties (error) (#6847)
Migrate fileURLToPath(import.meta.url) / dirname(...) boilerplate to the
native import.meta.dirname / import.meta.filename, then enable the rule
at error so new code stays on the native form.

The oxlint autofix rewrites the expression but leaves the now-unused
node:url / node:path imports behind (which the already-enabled
no-unused-vars=error would then flag), so this commit also removes those
34 orphaned imports — trimming the named import where other names are
still used, deleting the line where it was the sole import.

Scope is build scripts + Node-env tests only (config/scripts, tools/
benchmarks, *.test.{ts,mjs}, vitest configs); zero shipped runtime code.
The native properties are exact equivalents (Node >= 20.11; repo is on
24), so behavior is unchanged.

Verified: oxlint 0 errors tree-wide (root + mobile), oxfmt clean,
typecheck (node+cli+web) + mobile tsc pass, root vitest 22825 passed /
0 failed, mobile vitest 1018 passed. Exercised the rewritten scripts
directly: build:relay (6 targets), ensure-native-runtime,
verify-macos-entitlements all run correctly with import.meta.dirname.
2026-06-29 23:37:30 -07:00
Neil 3b5390acd9 fix(mobile): bump session max-lines ratchet to match file size (#6851)
mobile/app/h/[hostId]/session/[worktreeId].tsx grew past its 4988
counted-line ratchet (now 5015) in #6659 ("Show the git primary action
on mobile Source Control") without the override being bumped. That PR's
mobile CI passed because it branched off stale main where the file was
smaller; once merged, main went red for mobile lint — but mobile.yml
only runs on PRs touching mobile/, so no main-push build caught it.

Bump the per-file override 4988 -> 5015 to match the file's actual size
(what #6659 should have done), restoring green on every mobile-touching
PR. Per AGENTS.md the file should not carry a max-lines disable; this
keeps the tight per-file ratchet. The file is a candidate for a future
split, but that's a separate, owner-driven refactor.

Verified: mobile oxlint 0 errors, root oxlint 0 errors.
2026-06-29 23:24:35 -07:00
NeilandOrca 46646d7ff1 chore(lint): upgrade oxlint to 1.71 + enable 7 new rules (autofixed backlog) (#6841)
* chore(lint): upgrade oxlint to 1.71 and enable 7 new rules

Upgrade oxlint 1.67.0 -> 1.71.0 (1.72 was blocked by the repo's 3-day
minimum-release-age supply-chain guard; nothing here needs it). The
bump is a no-op on the existing config.

Enable 3 error rules (backlog autofixed to zero in this commit) and
4 warn rules (surface signal without gating CI):

error (autofixed, behavior-preserving):
- unicorn/prefer-node-protocol        (~1531 sites: bare builtin -> node:)
- typescript/no-import-type-side-effects (~36: all-inline-type -> import type)
- unicorn/no-array-reverse            (19: copy-then-reverse -> toReversed)

warn (real signal, current fires are test-only/correct):
- unicorn/no-array-fill-with-reference-type  (aliasing footgun guard)
- typescript/no-unsafe-function-type         (bans bare Function type)
- unicorn/prefer-array-flat-map              (map().flat() -> flatMap())
- unicorn/prefer-regexp-test                 (.match() in bool ctx -> .test())

mobile/.oxlintrc.json extends root, so it inherits all 7; the autofix
ran from root and covered mobile/ too.

Verification (all green): oxlint 0 errors (root+mobile+aux configs),
oxfmt clean, typecheck (node+cli+web), vitest 22795 passed / 0 failed,
builds (electron-vite + web + cli) succeed. node: rewrites confirmed to
skip embedded SSH/CLI string payloads (AST-only); all toReversed sites
verified to operate on fresh copies or write-once locals.

* chore(lint): bump mobile oxlint to 1.71 so inherited rules parse

mobile/ is a standalone pnpm project pinning its own oxlint@1.67, which
lacks unicorn/no-array-fill-with-reference-type (needs >=1.70). Since
mobile/.oxlintrc.json extends the root config, mobile CI's 'cd mobile &&
oxlint' failed to parse the new rule. Bump mobile to match root (1.71).

Verified in mobile/: oxlint 0 errors, oxfmt --check clean, tsc --noEmit
pass, vitest 978 passed / 0 failed.

Co-authored-by: Orca <help@stably.ai>

---------

Co-authored-by: Orca <help@stably.ai>
2026-06-29 22:38:29 -07:00
Brennan BensonandOrca a6f12f6120 Show the git primary action on mobile Source Control (#6659)
Co-authored-by: Orca <help@stably.ai>
2026-06-29 22:30:46 -07:00
Brennan Benson 3eb8d152e0 Prevent false mobile reconnects during active runtime traffic (#6805) 2026-06-29 18:08:16 -07:00
Jinjing 7caa582841 Show coding agent icons on mobile terminal tabs (#6792)
* Show coding agent icons on mobile terminal tabs

Move agent title decoration and terminal title parsing utilities
from the desktop renderer to shared code for reuse on mobile.

* Extract agent title stripping and terminal agent resolution to shared
* Implement mobile agent identity resolution and title-cleaning helpers
* Render agent icons on mobile terminal tabs when an agent is active
* Strip leading status glyphs from tab titles when showing an icon

* Suppress PTY resize on resume for mobile-driven terminals

Avoid reasserting the PTY size on resume if desktop resizing is
suppressed. This prevents overriding the intentional drift from
desktop dimensions for parked or mobile-driven terminals.
2026-06-29 16:06:27 -07:00
Brennan BensonandOrca 584cec78c3 fix(mobile): fail fast when iOS App Store train is closed (#6633)
Co-authored-by: Orca <help@stably.ai>
2026-06-29 14:08:23 -07:00
Brennan BensonandOrca 95aee5964e Bump mobile app.json to 0.0.17 (#6775)
Co-authored-by: Orca <help@stably.ai>
2026-06-29 12:37:04 -07:00
JinjingandOrca a8e6a91bcf fix: address review findings (#6710)
Co-authored-by: Orca <help@stably.ai>
2026-06-28 23:57:47 -07:00
Jinjing 31d35b14fc Fix mobile terminal close keyboard dismissal (#6681)
* fix: dismiss keyboard before tab actions

* fix: reset mobile tab sheet keyboard listener
2026-06-28 18:46:31 -07:00
Jinjing 93867ba05c fix: dismiss keyboard before tab actions (#6671) 2026-06-28 17:32:22 -07:00
Jinjing c50391df84 Support dictation and image attachments in mobile live input mode (#6603)
* Support dictation and image attachments in live terminal input mode

- Unify image attachment and voice dictation actions across both live
  and buffered terminal input views using a shared action bar.
- Route completed dictations directly to the active PTY (matching
  live keystroke semantics) when live mode is active, or append
  them to the input field in buffered mode.
- Add live terminal status headers to indicate mic activity and
  image upload progress.
- Include unit tests for the dictation routing logic.

* rm unused file
2026-06-28 01:20:00 -07:00
Jinjing 8a39450b18 refs/heads/handle-mobile-pull-request-issues (#6598)
* feat(mobile): add commit failure recovery panel with AI fix action

- Surfaces a "Commit failed" panel with a one-tap AI fix button when a
  git commit fails in the source control view or PR creation flow
- Detects commit failures specifically during the committing progress
  step and captures staged entries and commit message for context
- Extracts commit failure summary and prompt logic into
  `src/shared/source-control-commit-failure.ts` and PR checks prompt
  into `src/shared/pr-checks-fix-prompt.ts` so both desktop and mobile
  share the same implementations
- Adds auto-find of an available Metro port starting from 8081 and
  extracts expo CLI bootstrap into `mobile-expo-cli.mjs` shared by
  `start-emulator` and a new `start-expo.mjs` wrapper

* Share source-control AI prompts and simplify mobile PR actions

- Extract conflict, check-fixing, and commit-failure prompt builders
  to shared modules for reuse by both desktop and mobile.
- Configure Metro in the mobile package to watch and bundle modules
  from the repository-root shared directory.
- Remove the desktop-style merge method picker from the mobile PR
  actions panel, opting to use repository defaults automatically.
- Refactor mobile hosted review creation and git preparation logic
  into dedicated helper files.
2026-06-28 00:58:17 -07:00
Brennan Benson bed50606f2 Launch and detect Qwen Code via its qwen executable (#6530) 2026-06-27 22:02:52 -07:00
NeilandOrca 47f66f53f5 chore(deps): bump vite/esbuild/dompurify to clear Dependabot alerts (#6538)
Resolve security advisories without pnpm overrides:

Root:
- vite 7.3.5 -> 7.3.6 (widened esbuild range to ^0.27 || ^0.28)
- esbuild 0.27.7 -> 0.28.1 (GHSA dev-server advisory)
- dompurify 3.4.10 -> 3.4.11 (direct devDep)

Mobile:
- tsx ^4.21.0 -> ^4.22.4 (only hard esbuild consumer; pulls esbuild 0.28.1)
- vitest ^4.1.5 -> ^4.1.9, add explicit vite ^8.0.16 (-> 8.1.0)

Verified: typecheck:web, build:web, and full vitest suite (21246 passed)
all green.

Deferred (override-only, no plain-update path exists):
- dompurify 3.2.7 x18 — monaco-editor@0.55.1 hard-pins it exactly
- js-yaml@3 — @istanbuljs/load-nyc-config; uuid@7 — xcode@3.0.1;
  postcss@8.4 — @expo/metro-config (Expo SDK 55 lock)

Co-authored-by: Orca <help@stably.ai>
2026-06-27 22:01:16 -07:00