rnxsim 0.1.376 → 0.1.377

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (295) hide show
  1. package/README.md +28 -25
  2. package/cli/app-config.ts +9 -12
  3. package/cli/app-fonts.ts +3 -3
  4. package/cli/app-project.ts +8 -8
  5. package/cli/auth.ts +7 -9
  6. package/cli/bin.ts +16 -31
  7. package/cli/bridge-flow-runner.ts +3 -3
  8. package/cli/browser-backend.ts +44 -0
  9. package/cli/command-contract.ts +221 -0
  10. package/cli/command-registry.ts +291 -0
  11. package/cli/commands/agent-wrapper.ts +2 -2
  12. package/cli/commands/app-fonts.ts +2 -2
  13. package/cli/commands/assert.ts +3 -3
  14. package/cli/commands/auth.ts +1 -1
  15. package/cli/commands/box/cloud-box.ts +1 -1
  16. package/cli/commands/box/plane-share.ts +2 -2
  17. package/cli/commands/box.ts +4 -6
  18. package/cli/commands/compat.ts +1 -1
  19. package/cli/commands/config.ts +2 -2
  20. package/cli/commands/control.ts +29 -29
  21. package/cli/commands/cpu-profile.ts +7 -7
  22. package/cli/commands/daemon-mac-app.ts +7 -7
  23. package/cli/commands/daemon.ts +10 -10
  24. package/cli/commands/debug.ts +11 -11
  25. package/cli/commands/detox.ts +13 -13
  26. package/cli/commands/diagnose.ts +6 -6
  27. package/cli/commands/do-chain.ts +1 -2
  28. package/cli/commands/electron.ts +1 -3
  29. package/cli/commands/film.ts +3 -3
  30. package/cli/commands/flow.ts +43 -43
  31. package/cli/commands/inspect/count.ts +1 -1
  32. package/cli/commands/inspect/describe.ts +1 -1
  33. package/cli/commands/inspect/env.ts +2 -2
  34. package/cli/commands/inspect/get-layout.ts +1 -1
  35. package/cli/commands/inspect/keyboard.ts +1 -1
  36. package/cli/commands/inspect/list.ts +1 -1
  37. package/cli/commands/inspect/memory.ts +1 -1
  38. package/cli/commands/inspect/resolve-target.ts +1 -1
  39. package/cli/commands/inspect/screens.ts +1 -1
  40. package/cli/commands/inspect/tree.ts +1 -1
  41. package/cli/commands/inspect/url.ts +1 -1
  42. package/cli/commands/inspect/wait-event.ts +5 -5
  43. package/cli/commands/inspect.ts +34 -34
  44. package/cli/commands/install-desktop.ts +3 -3
  45. package/cli/commands/login.ts +6 -6
  46. package/cli/commands/maestro-generate.ts +5 -5
  47. package/cli/commands/maestro.ts +5 -5
  48. package/cli/commands/profile.ts +1 -1
  49. package/cli/commands/record.ts +9 -9
  50. package/cli/commands/runtime.ts +18 -18
  51. package/cli/commands/screenshot-command.ts +1 -1
  52. package/cli/commands/screenshot-layers.ts +5 -5
  53. package/cli/commands/screenshot-mode.ts +1 -1
  54. package/cli/commands/screenshot.ts +8 -8
  55. package/cli/commands/screenshots-capture.ts +5 -5
  56. package/cli/commands/serve.ts +3 -3
  57. package/cli/commands/setup.ts +20 -12
  58. package/cli/commands/skills.ts +5 -5
  59. package/cli/commands/slides.ts +1 -1
  60. package/cli/commands/telemetry.ts +1 -1
  61. package/cli/commands/three-mode.ts +1 -1
  62. package/cli/commands/timeline.ts +8 -8
  63. package/cli/commands/upgrade.ts +116 -131
  64. package/cli/commands/upload.ts +12 -12
  65. package/cli/commands/version.ts +7 -7
  66. package/cli/commands/what-happened.ts +9 -9
  67. package/cli/current-sim.ts +3 -3
  68. package/cli/desktop-companion.ts +1 -1
  69. package/cli/drivers/playwright.ts +9 -9
  70. package/cli/drivers/registry.ts +1 -1
  71. package/cli/drivers/types.ts +1 -1
  72. package/cli/flow-file.ts +2 -2
  73. package/cli/flow-session.ts +1 -1
  74. package/cli/help-core.ts +136 -0
  75. package/cli/help.ts +17 -53
  76. package/cli/hints.ts +5 -5
  77. package/cli/inspect-notice-state.ts +1 -1
  78. package/cli/maestro-js.ts +1 -1
  79. package/cli/outbound-endpoints.ts +23 -5
  80. package/cli/parse-args.ts +19 -66
  81. package/cli/recording-access.ts +1 -1
  82. package/cli/registry.ts +1 -0
  83. package/cli/run-registry.ts +1 -1
  84. package/cli/run-rnx-core.ts +148 -0
  85. package/cli/run-rnx.ts +6 -9
  86. package/cli/runtime-notes.ts +3 -3
  87. package/cli/standalone.ts +4 -0
  88. package/cli/ws-bridge.ts +8 -8
  89. package/detox/config-loader.ts +2 -2
  90. package/detox/index.ts +8 -8
  91. package/detox/jest-preset.cjs +1 -1
  92. package/detox/navigation.ts +2 -2
  93. package/dist-lib/agent-daemon-client.cjs +5 -5
  94. package/dist-lib/agent-events.cjs +1 -1
  95. package/dist-lib/agent-identity.cjs +2 -2
  96. package/dist-lib/agent-sessions.cjs +10 -10
  97. package/dist-lib/attached-projects.cjs +6 -6
  98. package/dist-lib/auth/shared-session.cjs +6 -6
  99. package/dist-lib/backend-origin.cjs +1 -1
  100. package/dist-lib/beta.cjs +1 -1
  101. package/dist-lib/beta.mjs +1 -1
  102. package/dist-lib/bridge-constants.cjs +1 -1
  103. package/dist-lib/bridge-contract-input.cjs +1 -1
  104. package/dist-lib/bridge-contract-input.mjs +1 -1
  105. package/dist-lib/bridge-contract.cjs +1 -1
  106. package/dist-lib/bridge-contract.mjs +1 -1
  107. package/dist-lib/cli-constants.cjs +1 -1
  108. package/dist-lib/config.cjs +25 -25
  109. package/dist-lib/detox/index.cjs +9 -9
  110. package/dist-lib/detox/jest-preset.cjs +1 -1
  111. package/dist-lib/dev-bundle-resolution.cjs +1 -1
  112. package/dist-lib/home-paths.cjs +29 -29
  113. package/dist-lib/host/bridge-host.cjs +128 -49
  114. package/dist-lib/host/fetch-proxy-handler.cjs +1 -1
  115. package/dist-lib/host/fetch-proxy-overrides.cjs +1 -1
  116. package/dist-lib/host/fetch-proxy-overrides.mjs +1 -1
  117. package/dist-lib/host/replacement-module-handler.cjs +1 -1
  118. package/dist-lib/host/websocket-proxy.cjs +1 -1
  119. package/dist-lib/index.cjs +14 -14
  120. package/dist-lib/jump-to-source-babel.cjs +1 -1
  121. package/dist-lib/menu.cjs +1 -1
  122. package/dist-lib/menu.mjs +1 -1
  123. package/dist-lib/metro-production-bundle.cjs +1 -1
  124. package/dist-lib/metro-production-bundle.mjs +1 -1
  125. package/dist-lib/metro.cjs +8 -8
  126. package/dist-lib/profiles.cjs +12 -12
  127. package/dist-lib/public-brand.cjs +1 -1
  128. package/dist-lib/react-native-host-modules.cjs +1 -1
  129. package/dist-lib/react-native-host-modules.mjs +1 -1
  130. package/dist-lib/render-mode.cjs +1 -1
  131. package/dist-lib/scripts/dev-server-scanner.cjs +8 -8
  132. package/dist-lib/sdk.cjs +1 -1
  133. package/dist-lib/sdk.mjs +1 -1
  134. package/dist-lib/skills.cjs +262 -135
  135. package/dist-lib/vite.cjs +9 -9
  136. package/package.json +4 -11
  137. package/scripts/dev-server-scanner.ts +2 -2
  138. package/scripts/optional-demo-registry.ts +1 -1
  139. package/skills/contrast/SKILL.md +3 -3
  140. package/skills/rnx-debug/SKILL.md +1 -1
  141. package/skills/rnx-test/SKILL.md +2 -2
  142. package/src/agent-identity.ts +1 -1
  143. package/src/agent-sessions.ts +7 -5
  144. package/src/cli-version.ts +12 -4
  145. package/src/config.ts +26 -28
  146. package/src/disk-cleanup.ts +11 -11
  147. package/src/home-paths.ts +28 -28
  148. package/src/host/bridge-host.ts +16 -16
  149. package/src/metro-plugin.ts +2 -2
  150. package/src/profiles.ts +2 -2
  151. package/src/runtime-assets.ts +7 -7
  152. package/src/runtime-delivery.ts +13 -13
  153. package/src/screenshots/orchestrate.ts +1 -1
  154. package/src/screenshots/schema.ts +2 -2
  155. package/src/skills/builtin/a11y-review.ts +2 -2
  156. package/src/skills/builtin/compat-check.ts +2 -2
  157. package/src/skills/builtin/maestro-test.ts +2 -2
  158. package/src/skills/builtin/perf-profile.ts +2 -2
  159. package/src/skills/builtin/screenshot-all.ts +2 -2
  160. package/src/skills/builtin/visual-diff.ts +2 -2
  161. package/src/skills/registry.ts +8 -8
  162. package/src/skills/types.ts +1 -1
  163. package/src/vite-plugin-one.ts +3 -3
  164. package/src/vite-plugin.ts +15 -2
  165. package/dist-cli/bin.js +0 -15
  166. package/dist-cli/chunks/agent-H42FCKFF.js +0 -48
  167. package/dist-cli/chunks/agent-wrapper-BBZKTZS6.js +0 -17
  168. package/dist-cli/chunks/app-fonts-43VXIKF4.js +0 -4
  169. package/dist-cli/chunks/assert-IXOLVO5Z.js +0 -49
  170. package/dist-cli/chunks/auth-KFMFB6FU.js +0 -12
  171. package/dist-cli/chunks/beta-5AO3SJB7.js +0 -4
  172. package/dist-cli/chunks/box-ZHM66L6K.js +0 -1730
  173. package/dist-cli/chunks/camera-FNJVFCDQ.js +0 -33
  174. package/dist-cli/chunks/chunk-37MCSPTE.js +0 -71
  175. package/dist-cli/chunks/chunk-3PEMSUAQ.js +0 -30
  176. package/dist-cli/chunks/chunk-4TQ5HOK3.js +0 -7
  177. package/dist-cli/chunks/chunk-5YZYDEMI.js +0 -4
  178. package/dist-cli/chunks/chunk-6CV3R3XD.js +0 -15
  179. package/dist-cli/chunks/chunk-7LGK5XU6.js +0 -4
  180. package/dist-cli/chunks/chunk-7R2TK2NY.js +0 -4
  181. package/dist-cli/chunks/chunk-7VZZQQEE.js +0 -497
  182. package/dist-cli/chunks/chunk-AFOVILIL.js +0 -130
  183. package/dist-cli/chunks/chunk-BEU7CD7E.js +0 -9
  184. package/dist-cli/chunks/chunk-CE4JQJ6Y.js +0 -6
  185. package/dist-cli/chunks/chunk-CIE6CZXL.js +0 -142
  186. package/dist-cli/chunks/chunk-CSJ7L7ZL.js +0 -312
  187. package/dist-cli/chunks/chunk-CWCQP53A.js +0 -27
  188. package/dist-cli/chunks/chunk-DCS5FK5N.js +0 -7
  189. package/dist-cli/chunks/chunk-DEV3E3MV.js +0 -4
  190. package/dist-cli/chunks/chunk-DGJMIVZM.js +0 -5
  191. package/dist-cli/chunks/chunk-DGX3MN65.js +0 -5
  192. package/dist-cli/chunks/chunk-DNPQMTW5.js +0 -4
  193. package/dist-cli/chunks/chunk-DOVBJBVD.js +0 -5
  194. package/dist-cli/chunks/chunk-DPBJ3S3J.js +0 -3
  195. package/dist-cli/chunks/chunk-FVZBGPCU.js +0 -4
  196. package/dist-cli/chunks/chunk-GDKMOIUT.js +0 -4
  197. package/dist-cli/chunks/chunk-GIF2NJCS.js +0 -32
  198. package/dist-cli/chunks/chunk-GZE57ORL.js +0 -4
  199. package/dist-cli/chunks/chunk-H3U56DKI.js +0 -24
  200. package/dist-cli/chunks/chunk-HZLOYAPH.js +0 -4
  201. package/dist-cli/chunks/chunk-J2IKAEU2.js +0 -4
  202. package/dist-cli/chunks/chunk-JXAXYK7W.js +0 -11
  203. package/dist-cli/chunks/chunk-KJE2O2GK.js +0 -4
  204. package/dist-cli/chunks/chunk-KMNVDZZI.js +0 -423
  205. package/dist-cli/chunks/chunk-LC3QRIRB.js +0 -10
  206. package/dist-cli/chunks/chunk-LGFTAQYC.js +0 -4
  207. package/dist-cli/chunks/chunk-LQMUA5IY.js +0 -4
  208. package/dist-cli/chunks/chunk-MFIQTWC5.js +0 -4
  209. package/dist-cli/chunks/chunk-MGALNF2F.js +0 -7
  210. package/dist-cli/chunks/chunk-MLBZZHOY.js +0 -4
  211. package/dist-cli/chunks/chunk-NNRF7GIB.js +0 -107
  212. package/dist-cli/chunks/chunk-NORLYTTO.js +0 -7
  213. package/dist-cli/chunks/chunk-P6KVGV3H.js +0 -14
  214. package/dist-cli/chunks/chunk-PAJTUK33.js +0 -4
  215. package/dist-cli/chunks/chunk-QELIC5XP.js +0 -4
  216. package/dist-cli/chunks/chunk-QRDF33WD.js +0 -11
  217. package/dist-cli/chunks/chunk-R76BA7C7.js +0 -535
  218. package/dist-cli/chunks/chunk-RVEB4CZ2.js +0 -4
  219. package/dist-cli/chunks/chunk-SK4M7NXT.js +0 -5
  220. package/dist-cli/chunks/chunk-SKMG5DD7.js +0 -5
  221. package/dist-cli/chunks/chunk-TEESPOYR.js +0 -4
  222. package/dist-cli/chunks/chunk-TH2UFGVP.js +0 -4
  223. package/dist-cli/chunks/chunk-TLP3T3VO.js +0 -4
  224. package/dist-cli/chunks/chunk-TZUABDIJ.js +0 -38
  225. package/dist-cli/chunks/chunk-UB2W6OQM.js +0 -99
  226. package/dist-cli/chunks/chunk-UYVXALPB.js +0 -506
  227. package/dist-cli/chunks/chunk-VQDYFFIG.js +0 -5
  228. package/dist-cli/chunks/chunk-VWCNJPCJ.js +0 -5
  229. package/dist-cli/chunks/chunk-VZIK4WIS.js +0 -74
  230. package/dist-cli/chunks/chunk-W3FNXAQP.js +0 -4
  231. package/dist-cli/chunks/chunk-XCDNVNP3.js +0 -4
  232. package/dist-cli/chunks/chunk-XSVILA4Z.js +0 -4
  233. package/dist-cli/chunks/chunk-XUTJ7ZWD.js +0 -4
  234. package/dist-cli/chunks/chunk-YTXY3MHW.js +0 -4
  235. package/dist-cli/chunks/chunk-ZF7PVX44.js +0 -28
  236. package/dist-cli/chunks/chunk-ZSSG7OR7.js +0 -4
  237. package/dist-cli/chunks/cleanup-MLOK2OZA.js +0 -25
  238. package/dist-cli/chunks/cli-version-OBNR366V.js +0 -4
  239. package/dist-cli/chunks/compat-SHMFSKU7.js +0 -23
  240. package/dist-cli/chunks/config-TPEAEUJ2.js +0 -13
  241. package/dist-cli/chunks/connect-3LEXWTE5.js +0 -4
  242. package/dist-cli/chunks/control-Z3FWA6BO.js +0 -4
  243. package/dist-cli/chunks/daemon-RSVYSC65.js +0 -4
  244. package/dist-cli/chunks/debug-GUVAK2KR.js +0 -200
  245. package/dist-cli/chunks/desktop-OOP2PTKP.js +0 -31
  246. package/dist-cli/chunks/detox-C2ILVBEC.js +0 -52
  247. package/dist-cli/chunks/device-NXIQQJWR.js +0 -18
  248. package/dist-cli/chunks/diagnose-2JBGYE5L.js +0 -43
  249. package/dist-cli/chunks/disk-cleanup-VURWJYQV.js +0 -4
  250. package/dist-cli/chunks/do-chain-DJ4UQC7A.js +0 -5
  251. package/dist-cli/chunks/drivers-JMA2OIKU.js +0 -4
  252. package/dist-cli/chunks/env-KTNPKEZR.js +0 -4
  253. package/dist-cli/chunks/film-DCPS7EID.js +0 -74
  254. package/dist-cli/chunks/flow-4DZ7B2OA.js +0 -4
  255. package/dist-cli/chunks/help-34CJMQY2.js +0 -4
  256. package/dist-cli/chunks/hidden-runtime-alias-HHT2C7WE.js +0 -4
  257. package/dist-cli/chunks/home-paths-KTPGCPMS.js +0 -4
  258. package/dist-cli/chunks/inspect-JF5WYJRD.js +0 -4
  259. package/dist-cli/chunks/install-desktop-ZIC4CDXI.js +0 -4
  260. package/dist-cli/chunks/login-TTJAOI2Q.js +0 -26
  261. package/dist-cli/chunks/logout-ERAQ6SKW.js +0 -4
  262. package/dist-cli/chunks/maestro-W46QCF77.js +0 -108
  263. package/dist-cli/chunks/maestro-generate-VBLM3MTU.js +0 -36
  264. package/dist-cli/chunks/mode-ZEDZK7R7.js +0 -26
  265. package/dist-cli/chunks/optional-demo-registry-ZUTPSVYQ.js +0 -4
  266. package/dist-cli/chunks/perf-YVT2WXT4.js +0 -48
  267. package/dist-cli/chunks/permissions-L7VVDHFP.js +0 -13
  268. package/dist-cli/chunks/platform-7TJOU2FB.js +0 -6
  269. package/dist-cli/chunks/privacy-57UOTB5J.js +0 -4
  270. package/dist-cli/chunks/record-VXG37P7U.js +0 -72
  271. package/dist-cli/chunks/report-issue-WNNOBZHC.js +0 -29
  272. package/dist-cli/chunks/reset-H5NBFE5U.js +0 -4
  273. package/dist-cli/chunks/resolve-target-57TK5WLE.js +0 -4
  274. package/dist-cli/chunks/runtime-QU2NIF2K.js +0 -4
  275. package/dist-cli/chunks/screenshot-command-AN56TTG7.js +0 -159
  276. package/dist-cli/chunks/screenshot-layers-3W5R7DB2.js +0 -20
  277. package/dist-cli/chunks/screenshots-capture-6AWJY7XZ.js +0 -42
  278. package/dist-cli/chunks/serve-GLYO5Q7J.js +0 -56
  279. package/dist-cli/chunks/setup-UA2HLD7S.js +0 -4
  280. package/dist-cli/chunks/sim-client-5C2RDQQO.js +0 -4
  281. package/dist-cli/chunks/skills-EYXWBRNQ.js +0 -50
  282. package/dist-cli/chunks/state-REJ7W6K3.js +0 -14
  283. package/dist-cli/chunks/storage-CFMDHI3V.js +0 -37
  284. package/dist-cli/chunks/store-XMCUA45G.js +0 -4
  285. package/dist-cli/chunks/telemetry-FBL3NAKB.js +0 -4
  286. package/dist-cli/chunks/timeline-HMCHN5FO.js +0 -24
  287. package/dist-cli/chunks/upgrade-2QSPAA3P.js +0 -7
  288. package/dist-cli/chunks/upload-DUQBKZYV.js +0 -4
  289. package/dist-cli/chunks/version-IOA6QFGB.js +0 -6
  290. package/dist-cli/chunks/web-NCGUYVCJ.js +0 -4
  291. package/dist-cli/chunks/welcome-QYGSQCWQ.js +0 -5
  292. package/dist-cli/chunks/what-happened-YTOUK4LO.js +0 -25
  293. package/dist-cli/chunks/ws-bridge-OF4OZARG.js +0 -4
  294. package/scripts/postinstall.cjs +0 -3
  295. package/scripts/preuninstall.cjs +0 -118
@@ -1,57 +1,43 @@
1
- // sootsim upgrade one command to get current.
2
- //
3
- // the sootsim CLI (the `sootsim` npm package) and the engine runtime (the
4
- // versioned tarball served to the browser/electron shell) are versioned
5
- // independently. that split is a frequent source of "I ran upgrade but the
6
- // version didn't change" confusion — the user upgraded one half. this
7
- // command checks and updates both:
8
- //
9
- // 1. CLI — query the npm registry; if behind, self-update the global
10
- // install with the same package manager that installed it
11
- // (bun/pnpm/npm, detected from the running binary's path).
12
- // npx-cache runs can't self-update in place, so those get
13
- // the exact command to run instead.
14
- // 2. runtime — delegate to `sootsim runtime install`, which resolves the
15
- // channel's latest, downloads + verifies
16
- // it, and activates.
17
- //
18
- // each half is a no-op when already current, so the command is safe to
19
- // run anytime.
20
-
21
- import { spawn } from 'node:child_process'
1
+ // rnx upgrade updates the separately delivered runtime first, then atomically
2
+ // replaces the standalone cli executable. runtime stays first because replacing
3
+ // the running cli's files before later dynamic imports can strand the command.
4
+
5
+ import { spawnSync } from 'node:child_process'
6
+ import { createHash } from 'node:crypto'
22
7
  import fs from 'node:fs'
23
- import os from 'node:os'
24
8
  import path from 'node:path'
25
9
  import { compareSemver } from '@contrast/runtime-delivery'
26
10
  import { getCliVersion } from '../../src/cli-version'
27
- import {
28
- isSootsimDevCheckout,
29
- readActiveRuntime,
30
- runtimeDir,
31
- sootsimHomeDir,
32
- } from '../../src/home-paths'
33
- import { resolveSootSimAppConfig } from '../app-config'
11
+ import { isSootsimDevCheckout, readActiveRuntime, runtimeDir } from '../../src/home-paths'
12
+ import { resolveRNXAppConfig } from '../app-config'
34
13
  import { fetchRuntimeReleaseNotes, formatRuntimeReleaseNotes } from '../runtime-notes'
14
+ import { IS_STANDALONE } from '../standalone'
35
15
  import { runRuntime } from './runtime'
36
16
 
37
- const REGISTRY_LATEST_URL = 'https://registry.npmjs.org/rnxsim/latest'
17
+ const DEFAULT_CLI_RELEASE_ORIGIN = 'https://r2.rnxsim.com/rnx-cli'
18
+ const CLI_VERSION_PATTERN = /^\d+\.\d+\.\d+(?:-[0-9A-Za-z.-]+)?$/
19
+ const SHA256_PATTERN = /^[a-f0-9]{64}$/
20
+
21
+ export interface UpgradeOptions {
22
+ cliExecutablePath?: string
23
+ cliReleaseOrigin?: string
24
+ standalone?: boolean
25
+ includeReleaseNotes?: boolean
26
+ }
38
27
 
39
- export async function runUpgrade(args: string[]): Promise<void> {
40
- // `--help` is handled upstream in bin.ts via the CLI registry (meta.ts) —
41
- // it never reaches here.
28
+ export async function runUpgrade(
29
+ args: string[],
30
+ options: UpgradeOptions = {},
31
+ ): Promise<void> {
42
32
  const channelIdx = args.indexOf('--channel')
43
33
  const channel =
44
34
  channelIdx >= 0 && args[channelIdx + 1] ? args[channelIdx + 1] : undefined
45
35
 
46
36
  console.log('rnx upgrade\n')
47
37
 
48
- // --- 1. engine runtime --------------------------------------------------
49
- // runtime first, CLI last: the CLI self-update replaces this process's
50
- // own dist files on disk, and any dynamic import after the swap resolves
51
- // against renamed chunk hashes and crashes (observed in a container run).
52
38
  console.log('runtime:')
53
39
  const beforeRuntime = readActiveRuntime()
54
- const { config } = await resolveSootSimAppConfig()
40
+ const { config } = await resolveRNXAppConfig()
55
41
  const configuredRuntime = config?.runtimeVersion
56
42
  const configuredRuntimeWasInstalled = configuredRuntime
57
43
  ? fs.existsSync(path.join(runtimeDir(configuredRuntime), 'index.html'))
@@ -84,125 +70,124 @@ export async function runUpgrade(args: string[]): Promise<void> {
84
70
  : ` result: v${installedRuntime} already current`,
85
71
  )
86
72
  }
87
- const releaseNotes = installedRuntime
88
- ? await fetchRuntimeReleaseNotes(installedRuntime)
89
- : null
73
+ const releaseNotes =
74
+ installedRuntime && options.includeReleaseNotes !== false
75
+ ? await fetchRuntimeReleaseNotes(installedRuntime)
76
+ : null
90
77
 
91
- // --- 2. CLI npm package -------------------------------------------------
92
78
  console.log('\ncli:')
93
- await upgradeCli()
79
+ await upgradeCli(options)
94
80
 
95
- if (installedRuntime) {
81
+ if (installedRuntime && options.includeReleaseNotes !== false) {
96
82
  console.log(`\n${formatRuntimeReleaseNotes(installedRuntime, releaseNotes)}`)
97
83
  }
98
84
  }
99
85
 
100
- type CliInstallKind =
101
- | { kind: 'dev' }
102
- | { kind: 'npx' }
103
- | { kind: 'global'; command: string; args: string[] }
104
-
105
- // how is this CLI process installed? keyed off the real path of the running
106
- // entry script — global installs land under each manager's global root,
107
- // npx/bunx runs land in their throwaway caches, and the Contrast monorepo dev
108
- // checkout runs from packages/sootsim.
109
- function detectCliInstall(): CliInstallKind {
110
- if (isSootsimDevCheckout()) return { kind: 'dev' }
111
- let real = process.argv[1] ?? ''
112
- try {
113
- real = fs.realpathSync(real)
114
- } catch {}
115
- const sep = path.sep
116
- if (real.includes(`${sep}_npx${sep}`) || real.includes(`${sep}.bunx${sep}`)) {
117
- return { kind: 'npx' }
118
- }
119
- if (real.includes(`${sep}.bun${sep}`)) {
120
- return { kind: 'global', command: 'bun', args: ['add', '-g', 'rnxsim@latest'] }
121
- }
122
- if (real.includes(`${sep}pnpm${sep}`)) {
123
- return { kind: 'global', command: 'pnpm', args: ['add', '-g', 'rnxsim@latest'] }
124
- }
125
- // the desktop splash installs the CLI into a user-writable prefix under the
126
- // sootsim home (`~/.sootsim/cli`) to dodge the EACCES a plain `npm i -g` hits
127
- // when npm's global prefix is a system-owned dir. self-update into that same
128
- // prefix so upgrade doesn't fall back to the unwritable global prefix.
129
- const cliPrefix = path.join(sootsimHomeDir(), 'cli')
130
- if (real.startsWith(`${cliPrefix}${sep}`)) {
131
- return {
132
- kind: 'global',
133
- command: 'npm',
134
- args: ['i', '-g', '--prefix', cliPrefix, 'rnxsim@latest'],
135
- }
136
- }
137
- const installerPrefix = path.resolve(
138
- process.env.SOOTSIM_CLI_PREFIX || path.join(os.homedir(), '.local'),
139
- )
140
- if (real.startsWith(`${installerPrefix}${sep}`)) {
141
- return {
142
- kind: 'global',
143
- command: 'npm',
144
- args: ['i', '-g', '--prefix', installerPrefix, 'rnxsim@latest'],
86
+ export async function upgradeCli(options: UpgradeOptions = {}): Promise<void> {
87
+ const standalone = options.standalone ?? IS_STANDALONE
88
+ if (!standalone) {
89
+ if (isSootsimDevCheckout()) {
90
+ console.log(' running from the Contrast checkout; pull instead of upgrading')
91
+ return
145
92
  }
93
+ throw new Error(
94
+ 'this is not the standalone rnx executable; reinstall from https://rnxsim.com/install.sh',
95
+ )
146
96
  }
147
- return { kind: 'global', command: 'npm', args: ['i', '-g', 'rnxsim@latest'] }
148
- }
149
97
 
150
- async function upgradeCli(): Promise<void> {
98
+ const releaseOrigin = (options.cliReleaseOrigin ?? DEFAULT_CLI_RELEASE_ORIGIN).replace(
99
+ /\/+$/,
100
+ '',
101
+ )
151
102
  const current = getCliVersion()
152
- const latest = await fetchLatestCliVersion()
153
-
154
- if (!latest) {
155
- console.log(` v${current} — couldn't reach the npm registry, skipped`)
156
- return
103
+ const latest = (await fetchRequired(`${releaseOrigin}/channels/stable`, 8_000))
104
+ .toString('utf8')
105
+ .trim()
106
+ if (!CLI_VERSION_PATTERN.test(latest)) {
107
+ throw new Error(
108
+ `rnx update service returned an invalid version: ${latest || '(empty)'}`,
109
+ )
157
110
  }
158
111
  if (compareSemver(latest, current) <= 0) {
159
112
  console.log(` v${current} (latest)`)
160
113
  return
161
114
  }
162
115
 
163
- const install = detectCliInstall()
164
- console.log(` v${current} v${latest}`)
165
-
166
- if (install.kind === 'dev') {
167
- console.log(` running from the Contrast dev checkout — pull instead of upgrading`)
168
- return
116
+ const artifact = cliArtifactName()
117
+ const artifactUrl = `${releaseOrigin}/${latest}/${artifact}`
118
+ const expectedSha = (await fetchRequired(`${artifactUrl}.sha256`, 8_000))
119
+ .toString('utf8')
120
+ .trim()
121
+ if (!SHA256_PATTERN.test(expectedSha)) {
122
+ throw new Error('rnx update service returned an invalid executable checksum')
169
123
  }
170
- if (install.kind === 'npx') {
171
- console.log(` running from the npx cache — get the latest with:`)
172
- console.log(` npx rnxsim@latest`)
173
- return
124
+
125
+ console.log(` v${current} v${latest}`)
126
+ console.log(` downloading ${artifact}...`)
127
+ const executable = await fetchRequired(artifactUrl, 120_000)
128
+ const actualSha = createHash('sha256').update(executable).digest('hex')
129
+ if (actualSha !== expectedSha) {
130
+ throw new Error(
131
+ `downloaded rnx executable failed verification (expected ${expectedSha}, got ${actualSha})`,
132
+ )
174
133
  }
175
134
 
176
- const printed = `${install.command} ${install.args.join(' ')}`
177
- console.log(` updating global install (${printed})…`)
178
- const ok = await runInherit(install.command, install.args)
179
- if (ok) {
180
- console.log(` updated to v${latest}`)
181
- } else {
182
- console.log(` update failed — run it yourself:`)
183
- console.log(` ${printed}`)
135
+ const executablePath = path.resolve(options.cliExecutablePath ?? process.execPath)
136
+ const tempDir = fs.mkdtempSync(path.join(path.dirname(executablePath), '.rnx-update-'))
137
+ const candidatePath = path.join(tempDir, path.basename(executablePath))
138
+ try {
139
+ fs.writeFileSync(candidatePath, executable, { mode: 0o755 })
140
+ fs.chmodSync(candidatePath, 0o755)
141
+ verifyCandidate(candidatePath, latest)
142
+ fs.renameSync(candidatePath, executablePath)
143
+ } finally {
144
+ fs.rmSync(tempDir, { recursive: true, force: true })
184
145
  }
146
+ console.log(` updated to v${latest}`)
185
147
  }
186
148
 
187
- function runInherit(command: string, args: string[]): Promise<boolean> {
188
- return new Promise((resolve) => {
189
- const child = spawn(command, args, { stdio: 'inherit' })
190
- child.on('error', () => resolve(false))
191
- child.on('exit', (code) => resolve(code === 0))
192
- })
149
+ function cliArtifactName(): string {
150
+ const platform = process.platform === 'darwin' ? 'darwin' : process.platform
151
+ if (platform !== 'darwin' && platform !== 'linux') {
152
+ throw new Error('standalone rnx self-update currently supports macOS and Linux')
153
+ }
154
+ if (process.arch !== 'arm64' && process.arch !== 'x64') {
155
+ throw new Error(`standalone rnx does not support ${process.arch}`)
156
+ }
157
+ return `rnx-${platform}-${process.arch}`
193
158
  }
194
159
 
195
- async function fetchLatestCliVersion(): Promise<string | null> {
160
+ async function fetchRequired(url: string, timeoutMs: number): Promise<Buffer> {
161
+ let response: Response
196
162
  try {
197
- // cap the registry lookup so a hung npm registry can't stall upgrade.
198
- const res = await fetch(REGISTRY_LATEST_URL, {
199
- headers: { accept: 'application/json' },
200
- signal: AbortSignal.timeout(8000),
163
+ response = await fetch(url, {
164
+ headers: { accept: 'application/octet-stream' },
165
+ signal: AbortSignal.timeout(timeoutMs),
201
166
  })
202
- if (!res.ok) return null
203
- const json = (await res.json()) as { version?: unknown }
204
- return typeof json.version === 'string' && json.version ? json.version : null
205
- } catch {
206
- return null
167
+ } catch (error) {
168
+ throw new Error(
169
+ `could not reach the rnx update service: ${
170
+ error instanceof Error ? error.message : String(error)
171
+ }`,
172
+ )
173
+ }
174
+ if (!response.ok) {
175
+ throw new Error(
176
+ `rnx update download failed: ${response.status} ${response.statusText}`,
177
+ )
178
+ }
179
+ return Buffer.from(await response.arrayBuffer())
180
+ }
181
+
182
+ function verifyCandidate(candidatePath: string, expectedVersion: string): void {
183
+ const result = spawnSync(candidatePath, ['--version'], {
184
+ encoding: 'utf8',
185
+ timeout: 15_000,
186
+ })
187
+ const reported = result.stdout.match(/^rnx v([^\s]+)/m)?.[1]
188
+ if (result.status !== 0 || reported !== expectedVersion) {
189
+ throw new Error(
190
+ `downloaded rnx executable reported ${reported ? `v${reported}` : 'no version'}; expected v${expectedVersion}`,
191
+ )
207
192
  }
208
193
  }
@@ -1,4 +1,4 @@
1
- // sootsim record upload — capture the currently-loaded bundle + device spec from
1
+ // rnx record upload — capture the currently-loaded bundle + device spec from
2
2
  // a running sootsim sim and POST it to the Contrast upload endpoint. returns a
3
3
  // /preview/<id> url that anyone can open to load this bundle in a frame.
4
4
  //
@@ -108,16 +108,16 @@ function readSnapshotManifest(manifestPath: string): AttachedInteractionSnapshot
108
108
  })
109
109
  }
110
110
 
111
- const REMOTE_DEFAULT_ORIGIN = process.env.SOOTSIM_UPLOAD_ORIGIN || 'https://contrast.dev'
111
+ const REMOTE_DEFAULT_ORIGIN = process.env.RNX_UPLOAD_ORIGIN || 'https://contrast.dev'
112
112
  // the canonical public preview link. Uploads go to the contrast backend, but
113
113
  // reviewers/users open SootSim preview pages on sootsim.com.
114
114
  const REMOTE_DEFAULT_PUBLIC_PREVIEW_ORIGIN =
115
- process.env.SOOTSIM_PREVIEW_ORIGIN || rnxPublicBrand.origin
115
+ process.env.RNX_PREVIEW_ORIGIN || rnxPublicBrand.origin
116
116
  export async function resolveDefaultUploadOrigin(
117
117
  explicitOrigin?: string,
118
118
  ): Promise<string> {
119
119
  if (explicitOrigin) return explicitOrigin
120
- if (process.env.SOOTSIM_UPLOAD_ORIGIN) return process.env.SOOTSIM_UPLOAD_ORIGIN
120
+ if (process.env.RNX_UPLOAD_ORIGIN) return process.env.RNX_UPLOAD_ORIGIN
121
121
  return REMOTE_DEFAULT_ORIGIN
122
122
  }
123
123
 
@@ -155,8 +155,8 @@ export function resolvePublicPreviewOrigin(
155
155
  explicitOrigin?: string,
156
156
  ): string {
157
157
  if (explicitOrigin) return normalizeOrigin(explicitOrigin)
158
- if (process.env.SOOTSIM_PREVIEW_ORIGIN) {
159
- return normalizeOrigin(process.env.SOOTSIM_PREVIEW_ORIGIN)
158
+ if (process.env.RNX_PREVIEW_ORIGIN) {
159
+ return normalizeOrigin(process.env.RNX_PREVIEW_ORIGIN)
160
160
  }
161
161
  if (isLoopbackOrigin(uploadOrigin)) return normalizeOrigin(uploadOrigin)
162
162
  if (isContrastOrigin(uploadOrigin)) {
@@ -174,11 +174,11 @@ usage:
174
174
 
175
175
  options:
176
176
  --origin <url> upload target (default: ${REMOTE_DEFAULT_ORIGIN})
177
- override with SOOTSIM_UPLOAD_ORIGIN env var
177
+ override with RNX_UPLOAD_ORIGIN env var
178
178
  --public-origin <url>
179
179
  public /preview link origin (default: ${REMOTE_DEFAULT_PUBLIC_PREVIEW_ORIGIN}
180
180
  for prod uploads, upload origin for localhost/custom origins).
181
- override with SOOTSIM_PREVIEW_ORIGIN env var
181
+ override with RNX_PREVIEW_ORIGIN env var
182
182
  --events <path> path to a gzipped events .jsonl.gz file to attach
183
183
  required unless --video is present; previews must
184
184
  have replay or recording playback data
@@ -216,7 +216,7 @@ options:
216
216
  examples:
217
217
  rnx record upload --events ./my-session.jsonl.gz
218
218
  rnx record upload --origin https://contrast.localhost:3000 --events ./my-session.jsonl.gz --open
219
- rnx record upload --video /tmp/sootsim-flow.mp4 --video-duration-ms 12000
219
+ rnx record upload --video /tmp/rnx-flow.mp4 --video-duration-ms 12000
220
220
  `)
221
221
  }
222
222
 
@@ -911,7 +911,7 @@ export async function runUpload(
911
911
  // asset-registry and are fetched once at engine boot — before the recorder
912
912
  // starts — so neither the manifest re-fetch nor recordedFetches captures
913
913
  // them and the /preview replay 404s. backfill them here via the shared
914
- // fetcher (same code path as the build's `sootsim app-fonts stage`) so both
914
+ // fetcher (same code path as the build's `rnx app-fonts stage`) so both
915
915
  // pipelines store identical bytes keyed by sha256(url).
916
916
  const appFontFiles: PreparedFile[] = []
917
917
  const appFontsWire = appFontsWireFromPageHref(snapshot.pageHref) || ''
@@ -1015,11 +1015,11 @@ export async function runUpload(
1015
1015
  bundleMinified: false,
1016
1016
  bundleOrigin,
1017
1017
  runtimeVersion: snapshot.runtimeVersion ?? undefined,
1018
- // config-only fonts resolved by `sootsim open` and carried on the engine
1018
+ // config-only fonts resolved by `rnx open` and carried on the engine
1019
1019
  // URL. persist them onto the share meta so /preview/<id> re-applies
1020
1020
  // `?appFonts=` and registers the same typefaces.
1021
1021
  appFonts: appFontsWire || undefined,
1022
- // configured splash (image + bg) resolved by `sootsim open`. persist it so
1022
+ // configured splash (image + bg) resolved by `rnx open`. persist it so
1023
1023
  // /preview/<id> re-applies `?appSplash=` and paints the same splash; the
1024
1024
  // image bytes are staged above so the engine's <img> resolves in preview.
1025
1025
  appSplash: appSplashWire || undefined,
@@ -1,4 +1,4 @@
1
- // sootsim version — one overview of both halves you're running.
1
+ // rnx version — one overview of both halves you're running.
2
2
  //
3
3
  // the `sootsim` CLI (npm package) and the engine runtime (versioned tarball
4
4
  // rendered in the browser/electron shell) are versioned independently, which
@@ -10,8 +10,8 @@ import fs from 'node:fs'
10
10
  import path from 'node:path'
11
11
  import { getCliVersion } from '../../src/cli-version'
12
12
  import { runtimeDir } from '../../src/home-paths'
13
- import { SOOTSIM_CHANGELOG_URL, sootsimRuntime } from '../../src/runtime-delivery'
14
- import { resolveSootSimAppConfig } from '../app-config'
13
+ import { RNX_CHANGELOG_URL, rnxRuntime } from '../../src/runtime-delivery'
14
+ import { resolveRNXAppConfig } from '../app-config'
15
15
  import { getRuntimeSummary } from '../runtime-summary'
16
16
 
17
17
  export async function runVersion(_args: string[]): Promise<void> {
@@ -20,7 +20,7 @@ export async function runVersion(_args: string[]): Promise<void> {
20
20
  console.log(`rnx v${getCliVersion()}${suffix}`)
21
21
 
22
22
  const runtime = getRuntimeSummary()
23
- const channel = sootsimRuntime.resolveChannel()
23
+ const channel = rnxRuntime.resolveChannel()
24
24
  if (runtime.isDevBridge) {
25
25
  console.log(runtime.primary)
26
26
  if (runtime.installedRuntime) console.log(`${runtime.installedRuntime} · ${channel}`)
@@ -30,7 +30,7 @@ export async function runVersion(_args: string[]): Promise<void> {
30
30
  console.log(`${runtime.primary} · ${channel}`)
31
31
  }
32
32
 
33
- const { config } = await resolveSootSimAppConfig()
33
+ const { config } = await resolveRNXAppConfig()
34
34
  if (config?.runtimeVersion) {
35
35
  const installed = fs.existsSync(
36
36
  path.join(runtimeDir(config.runtimeVersion), 'index.html'),
@@ -43,10 +43,10 @@ export async function runVersion(_args: string[]): Promise<void> {
43
43
  }
44
44
 
45
45
  // best-effort network check; never fail the command on a flaky network.
46
- const check = await sootsimRuntime.checkUpToDate({ channel })
46
+ const check = await rnxRuntime.checkUpToDate({ channel })
47
47
  if (check.outdated && check.latest) {
48
48
  console.log(`\n ↑ default runtime v${check.latest} available; run \`rnx upgrade\``)
49
49
  }
50
50
 
51
- console.log(`\n what's new: ${SOOTSIM_CHANGELOG_URL}`)
51
+ console.log(`\n what's new: ${RNX_CHANGELOG_URL}`)
52
52
  }
@@ -1,4 +1,4 @@
1
- // sootsim what-happened — show recent events from the semantic timeline
1
+ // rnx what-happened — show recent events from the semantic timeline
2
2
  //
3
3
  // the agent-facing read verb for SootSim.bridges.timeline. by default
4
4
  // shows everything since the previous CLI call from the same agent
@@ -6,13 +6,13 @@
6
6
  // the events it displayed so the next call shows only new events.
7
7
  //
8
8
  // usage:
9
- // sootsim what-happened # since last call
10
- // sootsim what-happened --summary # one-line counts
11
- // sootsim what-happened --all # full ring (no cursor)
12
- // sootsim what-happened --since 5s # absolute window
13
- // sootsim what-happened --kinds toast,fetch # filter
14
- // sootsim what-happened --json # structured
15
- // sootsim what-happened --limit 50 # cap (default 200)
9
+ // rnx what-happened # since last call
10
+ // rnx what-happened --summary # one-line counts
11
+ // rnx what-happened --all # full ring (no cursor)
12
+ // rnx what-happened --since 5s # absolute window
13
+ // rnx what-happened --kinds toast,fetch # filter
14
+ // rnx what-happened --json # structured
15
+ // rnx what-happened --limit 50 # cap (default 200)
16
16
 
17
17
  import { getCliIdentityKey } from '../current-sim'
18
18
  import { rnxExit } from '../run-rnx'
@@ -157,7 +157,7 @@ export async function runWhatHappened(args: string[], opts: WhatHappenedOptions)
157
157
  '--flow',
158
158
  // by default we hide high-frequency render/layout/scroll noise so
159
159
  // a single tap doesn't get buried under 1000+ rows. enable
160
- // `react-commit` with `sootsim timeline start react-commit`, then pass
160
+ // `react-commit` with `rnx timeline start react-commit`, then pass
161
161
  // `--noisy` (or an explicit `--kinds react-commit,…` filter) when you
162
162
  // actually want to see them.
163
163
  '--noisy',
@@ -16,7 +16,7 @@ interface CurrentSimState {
16
16
  // checked in order — the first one present wins. anything further down is a
17
17
  // progressively weaker signal of "same caller across invocations".
18
18
  const IDENTITY_ENV_VARS = [
19
- 'SOOTSIM_CLI_IDENTITY', // explicit override — fastest path, skips all pid lookups
19
+ 'RNX_CLI_IDENTITY', // explicit override — fastest path, skips all pid lookups
20
20
  'TM_SESSION', // Team Machine session id; routes prompt-bar followups back to this agent
21
21
  'CLAUDE_CODE_SESSION_ID', // claude code, if ever set
22
22
  'CODEX_THREAD_ID', // codex / openai agent thread, stable across tool invocations
@@ -54,7 +54,7 @@ export interface CliIdentity {
54
54
  // pids drift across invocations:
55
55
  // - claude code's bash tool spawns a fresh shell per call, so the
56
56
  // immediate gppid (the shell's parent) can change
57
- // - shell pipelines (`sootsim list | grep`) wrap the command in a
57
+ // - shell pipelines (`rnx list | grep`) wrap the command in a
58
58
  // subshell, adding an extra ppid layer that shifts gppid down by one
59
59
  // the topmost user process (just below init/launchd) is stable across
60
60
  // all of these — same agent / login shell / terminal across calls.
@@ -145,7 +145,7 @@ export function getCurrentSimPath() {
145
145
  return resolve(process.env[CURRENT_SIM_PATH_ENV])
146
146
  }
147
147
  const key = getCliIdentityKey()
148
- return join(tmpdir(), `sootsim-current-sim-${key}.json`)
148
+ return join(tmpdir(), `rnx-current-sim-${key}.json`)
149
149
  }
150
150
 
151
151
  export function readCurrentSim(): CurrentSimState | null {
@@ -240,7 +240,7 @@ export interface LaunchCompanionOptions {
240
240
  device?: string
241
241
  profileId?: string
242
242
  ephemeralProfile?: boolean
243
- // set by `sootsim open`, whose native window belongs to the launching
243
+ // set by `rnx open`, whose native window belongs to the launching
244
244
  // session. `sootsim desktop` omits it and remains a persistent desktop app.
245
245
  ownerPid?: number
246
246
  }
@@ -5,7 +5,7 @@
5
5
  // CLI invoked from a directory with no node_modules).
6
6
  //
7
7
  // the browser runs in a *detached* node subprocess (see PLAYWRIGHT_SIM_HOST)
8
- // rather than in this CLI process. that is load-bearing: `sootsim open`
8
+ // rather than in this CLI process. that is load-bearing: `rnx open`
9
9
  // returns the moment the sim connects, and playwright tears its browser
10
10
  // down when the launching process exits. an in-process launch would mean
11
11
  // the sim vanished the instant `open` finished. the detached host keeps the
@@ -49,7 +49,7 @@ const callerUserDataDir = process.env.SOOTSIM_PW_USERDATADIR || '';
49
49
  const ownerPid = Number(process.env.SOOTSIM_PW_OWNER_PID || 0);
50
50
  const ownerPollMs = Number(process.env.SOOTSIM_PW_OWNER_POLL_MS || 5000);
51
51
  // optional CDP port — exposes Chrome's remote-debugging endpoint so a
52
- // bridge-driven sim can also be cpu-profiled (sootsim perf cpu --cdp-port).
52
+ // bridge-driven sim can also be cpu-profiled (rnx perf cpu --cdp-port).
53
53
  // playwright keeps its own pipe connection; the port is an additional endpoint.
54
54
  const cdpPort = process.env.SOOTSIM_PW_CDP_PORT || '';
55
55
  // extra chromium launch args, space-separated. a linux GPU runner injects
@@ -93,7 +93,7 @@ const { join } = require('path');
93
93
  //
94
94
  // the prior approach was \`pgrep -f ms-playwright/[c]hromium\`. it never matched
95
95
  // system Chrome, so the reaper was a no-op in the common case and every
96
- // aborted/closed \`sootsim open\` leaked a renderer + gpu helper burning 100%+
96
+ // aborted/closed \`rnx open\` leaked a renderer + gpu helper burning 100%+
97
97
  // CPU until manually killed (multiple incidents 2026-06).
98
98
  //
99
99
  // fix: identify our chrome tree by its UNIQUE user-data-dir. every helper a
@@ -106,13 +106,13 @@ const reapEnabled = process.platform !== 'win32';
106
106
  let profileDir = callerUserDataDir;
107
107
  let ephemeralProfile = false;
108
108
  if (!profileDir) {
109
- profileDir = mkdtempSync(join(tmpdir(), 'sootsim-playwright-host-'));
109
+ profileDir = mkdtempSync(join(tmpdir(), 'rnx-playwright-host-'));
110
110
  ephemeralProfile = true;
111
111
  }
112
112
  // browser HTTP caches are acceleration data, not profile identity. give each
113
113
  // host a bounded temporary cache so persistent named profiles retain cookies
114
114
  // and storage without multiplying a private cache for every profile.
115
- const diskCacheDir = mkdtempSync(join(tmpdir(), 'sootsim-playwright-cache-'));
115
+ const diskCacheDir = mkdtempSync(join(tmpdir(), 'rnx-playwright-cache-'));
116
116
  const chromePidsByProfile = () => {
117
117
  if (!reapEnabled) return [];
118
118
  try {
@@ -283,7 +283,7 @@ const cleanupProfile = () => {
283
283
  // through shutdown(); the exit hook (sync sweep) still reaps the tree.
284
284
  process.on('exit', () => { reapChrome(); cleanupProfile(); });
285
285
  // owner-liveness watchdog — the load-bearing fix for leaked Chrome hosts.
286
- // we are spawned detached + unref'd so \`sootsim open\` returns immediately,
286
+ // we are spawned detached + unref'd so \`rnx open\` returns immediately,
287
287
  // which means nothing in the OS process tree ties Chrome's lifetime to the
288
288
  // session that asked for it. once the sim connects, the connect-timeout
289
289
  // safety net is cleared, so absent an explicit \`sootsim close\` (or the
@@ -312,7 +312,7 @@ const cleanupProfile = () => {
312
312
  // com.google.chrome.for.testing identity cannot intercept open/quit events for
313
313
  // the user's com.google.Chrome browser. CI may use chromium_headless_shell;
314
314
  // local rendering fails closed because that shell has no GPU and silently
315
- // chooses SwiftShader. NOTE: this is NOT enough to make \`sootsim perf cpu\`
315
+ // chooses SwiftShader. NOTE: this is NOT enough to make \`rnx perf cpu\`
316
316
  // work — that profiles the tenant *worker*, and the JS Self-Profiler API
317
317
  // cannot be constructed in a dedicated worker (see
318
318
  // worker-handlers/cpu-profile.ts). cpu-profile needs a CDP-based profiler
@@ -559,7 +559,7 @@ function resolveUserDataDir(opts: DriverLaunchOptions): string {
559
559
  return playwrightProfileUserDataDir(ensureProfile(opts.profileId).id)
560
560
  }
561
561
  if (opts.ephemeralProfile) {
562
- return mkdtempSync(join(tmpdir(), 'sootsim-playwright-profile-'))
562
+ return mkdtempSync(join(tmpdir(), 'rnx-playwright-profile-'))
563
563
  }
564
564
  return ''
565
565
  }
@@ -596,7 +596,7 @@ async function launch(opts: DriverLaunchOptions): Promise<DriverLaunchResult> {
596
596
 
597
597
  const errLog = join(
598
598
  tmpdir(),
599
- `sootsim-playwright-host-${Date.now().toString(36)}-${process.pid}.log`,
599
+ `rnx-playwright-host-${Date.now().toString(36)}-${process.pid}.log`,
600
600
  )
601
601
  const connectAckFile = `${errLog}.connected`
602
602
  const errFd = openSync(errLog, 'a')
@@ -37,7 +37,7 @@ export function resolveDriver(
37
37
  return null
38
38
  }
39
39
 
40
- // utility for the `sootsim list --drivers` view. returns a rich row per
40
+ // utility for the `rnx list --drivers` view. returns a rich row per
41
41
  // driver with availability + kind + description, suitable for a table.
42
42
  export interface DriverListRow {
43
43
  id: DriverId
@@ -85,7 +85,7 @@ export interface DriverLaunchResult {
85
85
 
86
86
  export interface Driver {
87
87
  id: DriverId
88
- // short human name shown in `sootsim list --drivers`.
88
+ // short human name shown in `rnx list --drivers`.
89
89
  name: string
90
90
  // one-line description. keep under 80 chars so the list command reads
91
91
  // nicely at default terminal width.
package/cli/flow-file.ts CHANGED
@@ -2,7 +2,7 @@ import * as fs from 'fs'
2
2
  import yaml from 'yaml'
3
3
 
4
4
  export interface FlowFrontmatter {
5
- // raw `sootsim open` target: port, dev-server URL, bundle URL, or shell URL
5
+ // raw `rnx open` target: port, dev-server URL, bundle URL, or shell URL
6
6
  app?: string | number
7
7
  device?: string
8
8
  // pin the sim color scheme for this flow run (screenshot baselines are
@@ -116,7 +116,7 @@ export function validateFlowSteps(steps: any[]): string[] {
116
116
  // structural-only validator used by CI runners before uploading the flow
117
117
  // artifact. we only check: file exists, parseable yaml, has at least one
118
118
  // real interaction step. playback validation is a separate concern handled
119
- // by `sootsim maestro end --validate` during the authoring session.
119
+ // by `rnx maestro end --validate` during the authoring session.
120
120
  export function validateFlowFile(flowPath: string): string[] {
121
121
  if (!fs.existsSync(flowPath)) {
122
122
  return [`file not found: ${flowPath}`]
@@ -25,7 +25,7 @@ const FLOW_SESSION_VERSION = 1 as const
25
25
 
26
26
  export function getFlowSessionPath() {
27
27
  return resolve(
28
- process.env.SOOTSIM_FLOW_SESSION_PATH || join(tmpdir(), 'sootsim-flow-session.json'),
28
+ process.env.RNX_FLOW_SESSION_PATH || join(tmpdir(), 'rnx-flow-session.json'),
29
29
  )
30
30
  }
31
31