stim 1.9.0 → 1.10.0

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 (83) hide show
  1. package/dist/{android-_y4Ohi5z.mjs → android-787HhP5w.mjs} +119 -29
  2. package/dist/{android-BPGizezh.mjs → android-DBkeHwpm.mjs} +168 -95
  3. package/dist/{android-DEgo4oCo.mjs → android-DPov-fv2.mjs} +2 -2
  4. package/dist/{android-cas-eiExNLf7.mjs → android-cas-CITmIeWY.mjs} +9 -8
  5. package/dist/android-cas-compiler.mjs +1 -1
  6. package/dist/{app-install-Uf3a83Tv.mjs → app-install-CrJ6t_bv.mjs} +2 -2
  7. package/dist/budget-BP4jZZL4.mjs +620 -0
  8. package/dist/build-progress-BXx-ZBe4.mjs +512 -0
  9. package/dist/{cache-manifest-Dg7OnMrp.mjs → cache-manifest-Pubfp8wV.mjs} +1 -1
  10. package/dist/cache-manifest.mjs +1 -1
  11. package/dist/cli.mjs +16 -16
  12. package/dist/collector-run.d.mts +5 -1
  13. package/dist/collector-run.mjs +7 -7
  14. package/dist/{command-output-gByVmIjy.mjs → command-output-D5z2_bcF.mjs} +1 -1
  15. package/dist/{config-Cp9lM3wX.mjs → config-BEq0Qw_a.mjs} +14 -131
  16. package/dist/{dependency-state-Bq5DcLGn.mjs → dependency-state-r9UesA9a.mjs} +2 -2
  17. package/dist/{deps-Cip5vUm1.mjs → deps-DP4eWqea.mjs} +3 -3
  18. package/dist/{detached-entry-KEu0_AXL.mjs → detached-entry-DJHoca49.mjs} +1 -1
  19. package/dist/{dev-client-HyqISM0h.mjs → dev-client-92U593KT.mjs} +137 -250
  20. package/dist/{device-D4U-xLty.mjs → device-DhTZe7L4.mjs} +7 -7
  21. package/dist/{build-lock-DPXPLgTc.mjs → device-lease-CbEaIk7b.mjs} +370 -12
  22. package/dist/{device-pool-CnTAz8X1.mjs → device-pool-Di8Q-9Ro.mjs} +4 -4
  23. package/dist/{device-remote-AQ5rQPqr.mjs → device-remote-Dy1jGj3U.mjs} +547 -468
  24. package/dist/{doctor-B_Ei3bZu.mjs → doctor-B-inAJmt.mjs} +58 -22
  25. package/dist/{error-diagnostics-Vfz83GCF.mjs → error-diagnostics-xxWKNO3-.mjs} +11 -12
  26. package/dist/{exec-jIAlgilk.mjs → exec-DK8KaVHK.mjs} +3 -2
  27. package/dist/{gc-Ckw8RQHi.mjs → gc-ChPFZMRC.mjs} +500 -1114
  28. package/dist/{guide-BiAbhs1J.mjs → guide-DwmaD_Wa.mjs} +882 -528
  29. package/dist/guide-status-CWvti2Lg.mjs +125 -0
  30. package/dist/idle-DpRLp5lj.mjs +157 -0
  31. package/dist/in-use-CjUluqIX.mjs +245 -0
  32. package/dist/{ios-BL2NFckr.mjs → ios-B2Fpqvlb.mjs} +25 -59
  33. package/dist/{ios-BzUJWk1K.mjs → ios-Dd-hYJBh.mjs} +130 -89
  34. package/dist/{ios-device-DPsSm0v_.mjs → ios-device-BiOsSVzd.mjs} +1 -1
  35. package/dist/{ios-device-D972i9wf.mjs → ios-device-CtRdEVjx.mjs} +3 -3
  36. package/dist/{launch-verify-Q_OtW1Rf.mjs → launch-verify-CQS_Kg-C.mjs} +5 -5
  37. package/dist/{logs-CI9NQSK7.mjs → logs-MARIy6m9.mjs} +9 -9
  38. package/dist/{metro-DrLHaMn2.mjs → metro-BWLOJ_Wr.mjs} +116 -10
  39. package/dist/{named-ports-CmLQSIRj.mjs → named-ports-DiTfSz6p.mjs} +4 -4
  40. package/dist/{ndjson-9uFNRwfe.mjs → ndjson-CDY9IkVC.mjs} +3 -56
  41. package/dist/{ndjson-DvHSsNU9.d.mts → ndjson-Du3j0AQ9.d.mts} +1 -0
  42. package/dist/{ownership-D15Op8vN.mjs → ownership-D2xbLVoz.mjs} +2 -3
  43. package/dist/ownership-DZjdx8Gq.mjs +1180 -0
  44. package/dist/{ports-BNKoWVWZ.mjs → ports-CLSSFOuz.mjs} +3 -3
  45. package/dist/{project-DS112DYB.mjs → project-BXZzOABt.mjs} +2 -2
  46. package/dist/{reload-ZNJUo1pl.mjs → reload-DoETJ3rl.mjs} +9 -10
  47. package/dist/{server-bare-DWkkcIxV.mjs → server-bare-DVbb7kXH.mjs} +1 -1
  48. package/dist/{server-expo-B_lctBR3.mjs → server-expo-BvOCeakp.mjs} +4 -4
  49. package/dist/server-expo-DBVTdult.mjs +2 -0
  50. package/dist/{settings-D030k0t4.mjs → settings-DOugPlPz.mjs} +16 -428
  51. package/dist/{settings-BKNh5rl4.mjs → settings-EWYNwe72.mjs} +16 -14
  52. package/dist/settings.schema.json +75 -0
  53. package/dist/{simslim-B_LsGLuJ.mjs → simslim-Ca3487H6.mjs} +182 -5
  54. package/dist/{slot-launch-DU9A-gYw.mjs → slot-launch-C5cg0fmk.mjs} +4 -4
  55. package/dist/{spawn-claims-Dn3C_N6w.mjs → spawn-claims-CUleC2cM.mjs} +1 -1
  56. package/dist/{start-DYkkKF0s.mjs → start-F9gv5dcC.mjs} +147 -98
  57. package/dist/start-VoFsPSes.mjs +2 -0
  58. package/dist/{state-NcJzMEBF.mjs → state-WGdIbi_d.mjs} +2 -2
  59. package/dist/{stats-DG9e66Rz.mjs → stats-BAgJaLA4.mjs} +1 -1
  60. package/dist/{stats-B63-JVAY.mjs → stats-DBYJ5bxL.mjs} +4 -4
  61. package/dist/{status-S6ehL4Ui.mjs → status-DLCD-o3s.mjs} +63 -231
  62. package/dist/status-Dr4fRkym.mjs +216 -0
  63. package/dist/{guide-status-BAMVU0ZA.mjs → stim-installations-CINXy_su.mjs} +3 -124
  64. package/dist/{stop-BO28HGqF.mjs → stop-Dj4pfmyv.mjs} +22 -18
  65. package/dist/{stop-T1R-cZRz.mjs → stop-ZvOeTmKb.mjs} +2 -2
  66. package/dist/supervisor-run.d.mts +11 -2
  67. package/dist/supervisor-run.mjs +185 -17
  68. package/dist/{workspace-process-lock-DWaiRD0e.mjs → workspace-process-lock-BXA96myD.mjs} +2 -2
  69. package/dist/workspaces-BTUyFfkv.mjs +1003 -0
  70. package/dist/{worktree-DKhSF0UX.mjs → worktree-4aZg2NnI.mjs} +1 -1
  71. package/dist/{worktree-LGB-UwgG.mjs → worktree-BMS7GeqB.mjs} +40 -122
  72. package/dist/{worktree-R_cUlE7s.mjs → worktree-BlizKDpZ.mjs} +143 -18
  73. package/dist/{xcode-BZqyxh3e.mjs → xcode-B2tBkf0m.mjs} +9 -158
  74. package/package.json +6 -5
  75. package/dist/build-progress-CVqkfPC6.mjs +0 -188
  76. package/dist/device-lease-Crs-HkJY.mjs +0 -366
  77. package/dist/logs-query-Cqma3WIu.mjs +0 -298
  78. package/dist/ownership-DCQPuWEc.mjs +0 -489
  79. package/dist/public-http-probe-CyMDrQ3c.mjs +0 -61
  80. package/dist/server-expo-CeILEu86.mjs +0 -2
  81. package/dist/sim-pool-KaIsp2Ft.mjs +0 -723
  82. package/dist/spawn-entry-nCE6m770.mjs +0 -14
  83. package/dist/workspace-state-DF2gCFhx.mjs +0 -169
@@ -1,6 +1,6 @@
1
- import { f as getProject } from "./config-Cp9lM3wX.mjs";
2
- import { o as findProjectRoot } from "./project-DS112DYB.mjs";
3
- import { n as getNamedPort, t as clearNamedPorts } from "./named-ports-CmLQSIRj.mjs";
1
+ import { f as getProject } from "./config-BEq0Qw_a.mjs";
2
+ import { o as findProjectRoot } from "./project-BXZzOABt.mjs";
3
+ import { n as getNamedPort, t as clearNamedPorts } from "./named-ports-DiTfSz6p.mjs";
4
4
  //#region src/commands/ports.ts
5
5
  async function inProject(action) {
6
6
  try {
@@ -1,5 +1,5 @@
1
- import { c as findEnclosingWorktreeRoot, f as getProject } from "./config-Cp9lM3wX.mjs";
2
- import { _ as repoRoot } from "./worktree-R_cUlE7s.mjs";
1
+ import { c as findEnclosingWorktreeRoot, f as getProject } from "./config-BEq0Qw_a.mjs";
2
+ import { y as repoRoot } from "./worktree-BlizKDpZ.mjs";
3
3
  import { existsSync, readFileSync, readdirSync, realpathSync } from "fs";
4
4
  import { basename, dirname, join, resolve } from "path";
5
5
  import { createRequire } from "module";
@@ -1,13 +1,12 @@
1
- import { U as deviceSlotPlatforms, W as parseDeviceSlotKey, f as getProject } from "./config-Cp9lM3wX.mjs";
2
- import { i as recordWorkspaceUse } from "./workspace-state-DF2gCFhx.mjs";
3
- import { o as findProjectRoot } from "./project-DS112DYB.mjs";
4
- import { d as readWorkspaceLaunches } from "./state-NcJzMEBF.mjs";
5
- import { c as resolveProjectMetro } from "./metro-DrLHaMn2.mjs";
6
- import { R as resolveOwnedAvdSerial } from "./android-_y4Ohi5z.mjs";
7
- import { f as refuseNoProject, l as phaseLine } from "./command-output-gByVmIjy.mjs";
8
- import { h as iosAppProcess, o as androidAppProcess } from "./app-install-Uf3a83Tv.mjs";
9
- import { C as resolveOwnedIosSim } from "./ios-BL2NFckr.mjs";
10
- import { n as nativeRunCommand } from "./slot-launch-DU9A-gYw.mjs";
1
+ import { B as parseDeviceSlotKey, f as getProject, z as deviceSlotPlatforms } from "./config-BEq0Qw_a.mjs";
2
+ import { h as recordWorkspaceUse, s as resolveProjectMetro } from "./metro-BWLOJ_Wr.mjs";
3
+ import { o as findProjectRoot } from "./project-BXZzOABt.mjs";
4
+ import { d as readWorkspaceLaunches } from "./state-WGdIbi_d.mjs";
5
+ import { f as refuseNoProject, l as phaseLine } from "./command-output-D5z2_bcF.mjs";
6
+ import { z as resolveOwnedAvdSerial } from "./android-787HhP5w.mjs";
7
+ import { S as resolveOwnedIosSim } from "./ios-B2Fpqvlb.mjs";
8
+ import { h as iosAppProcess, o as androidAppProcess } from "./app-install-CrJ6t_bv.mjs";
9
+ import { n as nativeRunCommand } from "./slot-launch-C5cg0fmk.mjs";
11
10
  import chalk from "chalk";
12
11
  import { WebSocket } from "ws";
13
12
  //#region src/engine/reload.ts
@@ -1,6 +1,6 @@
1
1
  import { i as __require, t as __commonJSMin } from "./rolldown-runtime-BsOwBuO_.mjs";
2
2
  import { n as supervisorError } from "./errors-B6W7FkxQ.mjs";
3
- import { S as projectMetroSharedCache } from "./settings-D030k0t4.mjs";
3
+ import { w as projectMetroSharedCache } from "./settings-DOugPlPz.mjs";
4
4
  import { a as metroStoreRoot, o as registerMetroStore, t as appendCacheStore } from "./metro-store-DzeWkfqW.mjs";
5
5
  import { createRequire } from "node:module";
6
6
  import { isAbsolute, join, relative, sep } from "node:path";
@@ -1,9 +1,9 @@
1
- import { t as getExecutor } from "./exec-jIAlgilk.mjs";
2
- import { r as createNdjsonWriter } from "./ndjson-9uFNRwfe.mjs";
3
- import { u as resolvePackageJson } from "./project-DS112DYB.mjs";
1
+ import { t as getExecutor } from "./exec-DK8KaVHK.mjs";
2
+ import { r as createNdjsonWriter } from "./ndjson-CDY9IkVC.mjs";
3
+ import { u as resolvePackageJson } from "./project-BXZzOABt.mjs";
4
4
  import { n as supervisorError } from "./errors-B6W7FkxQ.mjs";
5
5
  import { n as stripAnsi, t as createLineReader } from "./process-output-Fpl8PYi8.mjs";
6
- import { S as projectMetroSharedCache } from "./settings-D030k0t4.mjs";
6
+ import { w as projectMetroSharedCache } from "./settings-DOugPlPz.mjs";
7
7
  import { a as metroStoreRoot, i as metroStoreConfirmedRoot, n as expoMetroConfigPath, o as registerMetroStore, r as expoMetroStoreEnv } from "./metro-store-DzeWkfqW.mjs";
8
8
  import { accessSync, constants, existsSync, readFileSync } from "node:fs";
9
9
  import { LOG_ROTATE_BYTES } from "@stim-cli/core";
@@ -0,0 +1,2 @@
1
+ import { p as startExpoServer } from "./server-expo-BvOCeakp.mjs";
2
+ export { startExpoServer };
@@ -1,21 +1,11 @@
1
- import { d as getConfigPath, g as loadConfig, m as getRepoSettings, p as getProjectSettings } from "./config-Cp9lM3wX.mjs";
2
- import { _ as repoRoot, s as gitCommonDir } from "./worktree-R_cUlE7s.mjs";
1
+ import { d as getConfigPath$1, g as loadConfig$1, m as getRepoSettings, p as getProjectSettings } from "./config-BEq0Qw_a.mjs";
2
+ import { s as gitCommonDir, y as repoRoot } from "./worktree-BlizKDpZ.mjs";
3
3
  import { existsSync, readFileSync, realpathSync, statSync } from "fs";
4
4
  import { isAbsolute, join, relative, resolve, sep } from "path";
5
+ import { ANDROID_COMPILER_CACHE_CHOICES, ANDROID_PCH_CHOICES, REMOTE_DEVICE_BACKENDS, SETTINGS, SETTING_GROUPS, TUNNEL_MODES, acceptsShape, expectedShape, isLayeredSetting, settingDefinition, settingValueError } from "@stim-cli/core/state";
5
6
  import { isAbsolute as isAbsolute$1 } from "node:path";
6
7
  import { createHash } from "node:crypto";
7
8
  //#region src/optimizations.ts
8
- const ANDROID_COMPILER_CACHE_CHOICES = [
9
- "auto",
10
- "ccache",
11
- "cas",
12
- "none"
13
- ];
14
- const ANDROID_PCH_CHOICES = [
15
- "auto",
16
- "on",
17
- "off"
18
- ];
19
9
  function compilerCacheFallbackMessage({ fallback, compilerCache, file = null }) {
20
10
  const origin = fallback.fromEnvironment ? "the environment" : file;
21
11
  const backend = compilerCache === "none" ? "Android builds use no compiler cache, because optimizations.android.compilerCache is \"none\"." : "Android builds fall back to ccache when it is available.";
@@ -113,13 +103,6 @@ function resolveMetroSharedCache(settings) {
113
103
  }
114
104
  //#endregion
115
105
  //#region src/engine/metro-reach.ts
116
- const TUNNEL_MODES = [
117
- "auto",
118
- "off",
119
- "expo",
120
- "cloudflared",
121
- "ngrok"
122
- ];
123
106
  const PUBLIC_METRO_ENV = "STIM_METRO_PUBLIC_URL";
124
107
  const MANAGED_PROVIDERS = ["ngrok", "cloudflared"];
125
108
  const NAMED = {
@@ -161,409 +144,6 @@ function detectProviders(onPath) {
161
144
  return MANAGED_PROVIDERS.filter((p) => onPath(p));
162
145
  }
163
146
  //#endregion
164
- //#region src/workspace/settings-registry.ts
165
- const SETTING_SCOPES = [
166
- "machine",
167
- "workspace",
168
- "repo",
169
- "committed"
170
- ];
171
- const REMOTE_DEVICE_BACKENDS = ["proxy", "eas"];
172
- const IOS_SIMULATOR_APPS = [
173
- "xcode",
174
- "siniulator",
175
- "stim-desktop"
176
- ];
177
- const PROJECT = [
178
- "workspace",
179
- "repo",
180
- "committed"
181
- ];
182
- const EVERY = [
183
- "machine",
184
- "workspace",
185
- "repo",
186
- "committed"
187
- ];
188
- const MACHINE = ["machine"];
189
- const STRING = { kind: "string" };
190
- const PATH = { kind: "path" };
191
- const ABSOLUTE_PATH = {
192
- kind: "path",
193
- absolute: true
194
- };
195
- const RELATIVE_PATH = {
196
- kind: "path",
197
- relative: true
198
- };
199
- const BOOLEAN = { kind: "boolean" };
200
- const OBJECT = { kind: "object" };
201
- const REMOTE = {
202
- kind: "choice",
203
- choices: REMOTE_DEVICE_BACKENDS
204
- };
205
- const PARKED_MAX = {
206
- kind: "number",
207
- integer: true,
208
- minimum: 0
209
- };
210
- const CAPACITY = {
211
- kind: "number",
212
- integer: true,
213
- minimum: 0
214
- };
215
- function optimization(key, description, type = BOOLEAN) {
216
- return {
217
- key: `optimizations.${key}`,
218
- type,
219
- scopes: EVERY,
220
- description,
221
- ...type.kind === "boolean" ? { default: true } : {}
222
- };
223
- }
224
- const SETTINGS = [
225
- optimization("buildCache", "Read and write native build artifacts"),
226
- optimization("remoteBuildCache", "Use remote artifact providers"),
227
- optimization("releaseBundleSwap", "Swap current JS into cached release builds"),
228
- optimization("metroSharedCache", "Append Stim's shared Metro cache store"),
229
- optimization("metroWarmup", "Prefetch the development bundle during ios and android"),
230
- optimization("ios.compilationCache", "Xcode compilation caching"),
231
- {
232
- key: "optimizations.ios.swiftCompilationCache",
233
- type: BOOLEAN,
234
- scopes: EVERY,
235
- description: "Swift compilation caching; unset detects toolchain support"
236
- },
237
- optimization("ios.prefixMapping", "Clang source and DerivedData prefix mapping"),
238
- {
239
- ...optimization("android.compilerCache", "Android compiler cache backend", {
240
- kind: "choice",
241
- choices: ANDROID_COMPILER_CACHE_CHOICES
242
- }),
243
- default: "auto"
244
- },
245
- {
246
- ...optimization("android.casToolchain", "Absolute path to the Android CAS toolchain manifest", ABSOLUTE_PATH),
247
- env: "STIM_ANDROID_CAS_TOOLCHAIN"
248
- },
249
- {
250
- ...optimization("android.pch", "Android precompiled headers", {
251
- kind: "choice",
252
- choices: ANDROID_PCH_CHOICES
253
- }),
254
- default: "auto"
255
- },
256
- optimization("android.gradleBuildCache", "Gradle build cache"),
257
- optimization("android.targetAbiOnly", "Narrow Debug builds to the device ABI"),
258
- {
259
- key: "ios.deviceType",
260
- type: STRING,
261
- scopes: PROJECT,
262
- description: "Simulator model for owned simulators"
263
- },
264
- {
265
- key: "ios.runtime",
266
- type: STRING,
267
- scopes: PROJECT,
268
- description: "iOS runtime owned simulators are created on"
269
- },
270
- {
271
- key: "ios.configuration",
272
- type: STRING,
273
- scopes: PROJECT,
274
- default: "Debug",
275
- description: "Xcode configuration to build, such as Debug or Release"
276
- },
277
- {
278
- key: "ios.remote",
279
- type: REMOTE,
280
- scopes: PROJECT,
281
- description: "Default remote backend for iOS"
282
- },
283
- {
284
- key: "ios.simslimProfile",
285
- type: RELATIVE_PATH,
286
- scopes: PROJECT,
287
- description: "SimSlim JSON profile under the app"
288
- },
289
- {
290
- key: "ios.signingIdentity",
291
- type: STRING,
292
- scopes: PROJECT,
293
- description: "Keychain identity used to re-seal a device build"
294
- },
295
- {
296
- key: "ios.signingIdentitySha1",
297
- type: {
298
- kind: "string",
299
- pattern: "^[0-9A-Fa-f]{40}$",
300
- patternHelp: "a 40-character hex SHA-1 hash"
301
- },
302
- scopes: PROJECT,
303
- description: "SHA-1 of the signing identity, when two share a name"
304
- },
305
- {
306
- key: "ios.lanHost",
307
- type: {
308
- kind: "string",
309
- pattern: "^(?!-)[A-Za-z0-9-]+(?:\\.(?!-)[A-Za-z0-9-]+)*$",
310
- patternHelp: "a bare address or hostname, never a URL, scheme, or port"
311
- },
312
- scopes: PROJECT,
313
- description: "Address a phone uses to reach this workspace's Metro"
314
- },
315
- {
316
- key: "android.systemImage",
317
- type: STRING,
318
- scopes: PROJECT,
319
- description: "SDK system image for owned AVDs"
320
- },
321
- {
322
- key: "android.dataPartitionSizeGb",
323
- type: {
324
- kind: "number",
325
- integer: true,
326
- minimum: 6,
327
- maximum: 16384
328
- },
329
- scopes: PROJECT,
330
- default: 8,
331
- description: "Data partition size of a new owned AVD, in GiB"
332
- },
333
- {
334
- key: "android.avdConfigFile",
335
- type: RELATIVE_PATH,
336
- scopes: PROJECT,
337
- description: "AVD config.ini fragment under the app"
338
- },
339
- {
340
- key: "android.avdConfig",
341
- type: OBJECT,
342
- scopes: PROJECT,
343
- description: "Validated AVD config values"
344
- },
345
- {
346
- key: "android.variant",
347
- type: STRING,
348
- scopes: PROJECT,
349
- description: "Gradle build variant"
350
- },
351
- {
352
- key: "android.keystore",
353
- type: PATH,
354
- scopes: PROJECT,
355
- description: "Keystore a re-packed release APK is signed with"
356
- },
357
- {
358
- key: "android.keystorePassword",
359
- type: STRING,
360
- scopes: PROJECT,
361
- sensitive: true,
362
- description: "Keystore password, or an apksigner env: or file: reference"
363
- },
364
- {
365
- key: "android.remote",
366
- type: REMOTE,
367
- scopes: PROJECT,
368
- description: "Default remote backend for Android"
369
- },
370
- {
371
- key: "metro.tunnel",
372
- type: {
373
- kind: "choice",
374
- choices: TUNNEL_MODES
375
- },
376
- scopes: PROJECT,
377
- default: "auto",
378
- description: "How a remote device reaches Metro"
379
- },
380
- {
381
- key: "metro.ngrokUrl",
382
- type: STRING,
383
- scopes: PROJECT,
384
- description: "Stable ngrok URL for the managed tunnel"
385
- },
386
- {
387
- key: "metro.publicUrl",
388
- type: STRING,
389
- scopes: PROJECT,
390
- description: "Existing public Metro URL"
391
- },
392
- {
393
- key: "metro.warmupUrl.ios",
394
- type: { kind: "bundle-url" },
395
- scopes: PROJECT,
396
- description: "Bundle URL `stim ios` prefetches to warm Metro"
397
- },
398
- {
399
- key: "metro.warmupUrl.android",
400
- type: { kind: "bundle-url" },
401
- scopes: PROJECT,
402
- description: "Bundle URL `stim android` prefetches to warm Metro"
403
- },
404
- {
405
- key: "worktree.exclude",
406
- type: { kind: "strings" },
407
- scopes: ["repo", "committed"],
408
- committedAt: "repository",
409
- description: "Ignored paths `worktree warm` skips"
410
- },
411
- {
412
- key: "worktree.defaultBranch",
413
- type: STRING,
414
- scopes: ["repo", "committed"],
415
- committedAt: "repository",
416
- description: "Branch `worktree warm --refresh` expects the source checkout on"
417
- },
418
- {
419
- key: "cache.provider",
420
- type: STRING,
421
- scopes: PROJECT,
422
- description: "Second-tier cache provider module"
423
- },
424
- {
425
- key: "cache.options",
426
- type: OBJECT,
427
- scopes: PROJECT,
428
- description: "Options passed to the cache provider"
429
- },
430
- {
431
- key: "iosSimulatorApp",
432
- type: {
433
- kind: "choice",
434
- choices: IOS_SIMULATOR_APPS
435
- },
436
- scopes: MACHINE,
437
- default: "xcode",
438
- description: "App that displays an owned iOS simulator"
439
- },
440
- {
441
- key: "concurrency.maxBuilds",
442
- type: CAPACITY,
443
- scopes: MACHINE,
444
- default: 0,
445
- env: "STIM_MAX_BUILDS",
446
- description: "Concurrent native builds; 0 means no limit"
447
- },
448
- {
449
- key: "concurrency.maxDevices",
450
- type: CAPACITY,
451
- scopes: MACHINE,
452
- default: 0,
453
- env: "STIM_MAX_DEVICES",
454
- description: "Booted owned devices; 0 means no limit"
455
- },
456
- {
457
- key: "pool.iosParkedMax",
458
- type: PARKED_MAX,
459
- scopes: MACHINE,
460
- default: 3,
461
- env: "STIM_POOL_IOS_PARKED_MAX",
462
- scopedHomeValue: 0,
463
- description: "Parked simulators kept for adoption; 0 turns parking off"
464
- },
465
- {
466
- key: "pool.androidParkedMax",
467
- type: PARKED_MAX,
468
- scopes: MACHINE,
469
- default: 3,
470
- env: "STIM_POOL_ANDROID_PARKED_MAX",
471
- scopedHomeValue: 0,
472
- description: "Parked emulators kept for adoption; 0 turns parking off"
473
- },
474
- {
475
- key: "caches.buildCache",
476
- type: ABSOLUTE_PATH,
477
- scopes: MACHINE,
478
- env: "STIM_BUILD_CACHE",
479
- description: "Absolute path of the shared build cache"
480
- },
481
- {
482
- key: "caches.metroCache",
483
- type: ABSOLUTE_PATH,
484
- scopes: MACHINE,
485
- env: "STIM_METRO_CACHE",
486
- description: "Absolute parent path of the Metro transform caches"
487
- },
488
- {
489
- key: "tempDir",
490
- type: ABSOLUTE_PATH,
491
- scopes: MACHINE,
492
- env: "STIM_TMPDIR",
493
- description: "Absolute directory for large temporary copies"
494
- }
495
- ];
496
- const BY_KEY = new Map(SETTINGS.map((setting) => [setting.key, setting]));
497
- function settingDefinition(key) {
498
- return BY_KEY.get(key) ?? null;
499
- }
500
- function isLayeredSetting(setting) {
501
- return setting.scopes.some((scope) => scope !== "machine");
502
- }
503
- const SETTING_GROUPS = [...new Set(SETTINGS.filter(isLayeredSetting).flatMap((setting) => setting.key.split(".").slice(0, -1).map((_, index, parts) => parts.slice(0, index + 1).join("."))))];
504
- function isPlainObject$1(value) {
505
- return value !== null && typeof value === "object" && !Array.isArray(value);
506
- }
507
- function bundleUrlAccepts(value, key) {
508
- if (typeof value !== "string" || !/^(https?:\/\/|\/(?!\/))/.test(value) || /[\s\\#]/.test(value)) return false;
509
- try {
510
- const url = new URL(value, "http://localhost");
511
- return /\.bundle\/*$/.test(url.pathname) && url.searchParams.get("platform") === key.split(".").at(-1);
512
- } catch {
513
- return false;
514
- }
515
- }
516
- function expectedShape(type) {
517
- switch (type.kind) {
518
- case "boolean": return "true or false";
519
- case "string": return "a string";
520
- case "path": return "a string path";
521
- case "strings": return "an array of strings";
522
- case "number": return "a number";
523
- case "choice": return `one of: ${type.choices.join(", ")}`;
524
- case "object": return "an object";
525
- case "bundle-url": return "an HTTP(S) URL or /path ending in .bundle with a matching platform query and no fragment";
526
- }
527
- }
528
- function acceptsShape(setting, value) {
529
- const { type } = setting;
530
- switch (type.kind) {
531
- case "boolean": return typeof value === "boolean";
532
- case "string":
533
- case "path": return typeof value === "string";
534
- case "strings": return Array.isArray(value) && value.every((entry) => typeof entry === "string");
535
- case "number": return typeof value === "number";
536
- case "choice": return typeof value === "string" && type.choices.includes(value);
537
- case "object": return isPlainObject$1(value);
538
- case "bundle-url": return bundleUrlAccepts(value, setting.key);
539
- }
540
- }
541
- function numberBounds(type) {
542
- const noun = type.integer ? "a whole number" : "a number";
543
- if (type.minimum !== void 0 && type.maximum !== void 0) return `${noun} from ${type.minimum} through ${type.maximum}`;
544
- if (type.minimum !== void 0) return `${noun}, ${type.minimum} or more`;
545
- return noun;
546
- }
547
- function settingValueError(setting, value) {
548
- const { type } = setting;
549
- if (!acceptsShape(setting, value)) return type.kind === "number" ? numberBounds(type) : expectedShape(type);
550
- if (type.kind === "number") {
551
- const number = value;
552
- if (!Number.isFinite(number) || type.integer && !Number.isSafeInteger(number) || type.minimum !== void 0 && number < type.minimum || type.maximum !== void 0 && number > type.maximum) return numberBounds(type);
553
- }
554
- if (type.kind === "path") {
555
- const path = value;
556
- if (type.absolute && !isAbsolute$1(path)) return "an absolute path";
557
- if (type.relative && (path.trim() === "" || isAbsolute$1(path))) return "a relative path inside the app directory";
558
- }
559
- if (type.kind === "string" && type.pattern && !new RegExp(type.pattern).test(value)) return type.patternHelp ?? `a string matching ${type.pattern}`;
560
- return null;
561
- }
562
- const SENSITIVE_REFERENCE = /^(env|file):\S/;
563
- function isSensitiveReference(value) {
564
- return typeof value === "string" && SENSITIVE_REFERENCE.test(value);
565
- }
566
- //#endregion
567
147
  //#region src/workspace/settings.ts
568
148
  function isPlainObject(v) {
569
149
  return v !== null && typeof v === "object" && !Array.isArray(v);
@@ -579,6 +159,7 @@ function mergeSettingsLayers(layers) {
579
159
  }
580
160
  const LAYERED_SETTINGS = SETTINGS.filter(isLayeredSetting);
581
161
  const KNOWN_SETTINGS = /* @__PURE__ */ new Set([...LAYERED_SETTINGS.map((setting) => setting.key), ...SETTING_GROUPS]);
162
+ const BOUNDS_CHECKED_WHEN_USED = /* @__PURE__ */ new Set(["android.dataPartitionSizeGb"]);
582
163
  const SETTINGS_WITH_RESOLVE_TIME_FALLBACK = /* @__PURE__ */ new Set(["optimizations.android.casToolchain"]);
583
164
  const PATH_SETTINGS = Object.freeze(LAYERED_SETTINGS.filter((setting) => setting.type.kind === "path").map((setting) => setting.key));
584
165
  function settingValueAt(settings, path) {
@@ -599,8 +180,9 @@ function settingShapeErrors(settings) {
599
180
  for (const setting of LAYERED_SETTINGS) {
600
181
  if (SETTINGS_WITH_RESOLVE_TIME_FALLBACK.has(setting.key)) continue;
601
182
  const value = settingValueAt(settings, setting.key);
602
- if (value === void 0 || acceptsShape(setting, value)) continue;
603
- errors.push(`Invalid ${setting.key} setting ${JSON.stringify(value)}. Expected ${expectedShape(setting.type)}.`);
183
+ if (value === void 0) continue;
184
+ const expected = setting.type.kind === "number" && !BOUNDS_CHECKED_WHEN_USED.has(setting.key) ? settingValueError(setting, value) : acceptsShape(setting, value) ? null : expectedShape(setting.type);
185
+ if (expected) errors.push(`Invalid ${setting.key} setting ${JSON.stringify(value)}. Expected ${expected}.`);
604
186
  }
605
187
  return errors;
606
188
  }
@@ -873,8 +455,8 @@ function readCommittedSettings(directory) {
873
455
  }
874
456
  }
875
457
  function settingsLayers({ projectPath, gitCommonDir, repoRoot }) {
876
- const machine = loadConfig();
877
- const machineFile = getConfigPath();
458
+ const machine = loadConfig$1();
459
+ const machineFile = getConfigPath$1();
878
460
  const committedDir = projectPath ?? repoRoot;
879
461
  return [
880
462
  projectPath ? {
@@ -982,6 +564,12 @@ function remoteSetting(settings, platform) {
982
564
  const remote = block.remote;
983
565
  return typeof remote === "string" && REMOTE_DEVICE_BACKENDS.includes(remote) ? remote : null;
984
566
  }
567
+ function metroIdleStopMinutesSetting(settings) {
568
+ const block = settings.metro;
569
+ const value = typeof block === "object" && block !== null ? block.idleStopMinutes : void 0;
570
+ const setting = settingDefinition("metro.idleStopMinutes");
571
+ return setting && value !== void 0 && settingValueError(setting, value) === null ? value : Number(setting?.default);
572
+ }
985
573
  function tunnelModeSetting(settings) {
986
574
  const block = settings.metro;
987
575
  if (typeof block !== "object" || block === null) return null;
@@ -1020,4 +608,4 @@ function normalizedHttpsUrl(raw) {
1020
608
  }
1021
609
  }
1022
610
  //#endregion
1023
- export { settingFile as A, isSensitiveReference as B, projectOptimizations as C, remoteIosSetting as D, remoteAndroidSetting as E, unknownSettingKeys as F, planMetroReach as G, settingValueError as H, IOS_SIMULATOR_APPS as I, optimizationBuildProfile as J, artifactCachePolicy as K, REMOTE_DEVICE_BACKENDS as L, settingShapeErrors as M, settingsLayers as N, resolveCacheProviderConfig as O, tunnelModeSetting as P, SETTINGS as R, projectMetroSharedCache as S, readCommittedSettings as T, PUBLIC_METRO_ENV as U, settingDefinition as V, detectProviders as W, resolveOptimizations as Y, iosSimSlimProfileSetting as _, androidAvdConfigSetting as a, metroWarmupUrlSetting as b, androidDataPartitionSizeGbSetting as c, iosLanHostSetting as d, iosLanHostSettingError as f, iosSigningIdentitySha1SettingError as g, iosSigningIdentitySha1Setting as h, SETTING_SHAPE_REMEDY as i, settingOrigin as j, resolveSettings as k, androidDataPartitionSizeGbSettingError as l, iosSigningIdentitySettingError as m, PATH_SETTINGS as n, androidAvdConfigSettingError as o, iosSigningIdentitySetting as p, compilerCacheFallbackMessage as q, SETTINGS_WITH_RESOLVE_TIME_FALLBACK as r, androidDataPartitionSizeBytes as s, ANDROID_AVD_CONFIG_HELP as t, cacheProviderSettingError as u, mergeSettingsLayers as v, publicUrlSetting as w, ngrokUrlSetting as x, metroTunnelSettingError as y, SETTING_SCOPES as z };
611
+ export { resolveCacheProviderConfig as A, planMetroReach as B, ngrokUrlSetting as C, readCommittedSettings as D, publicUrlSetting as E, settingsLayers as F, compilerCacheFallbackMessage as H, tunnelModeSetting as I, unknownSettingKeys as L, settingFile as M, settingOrigin as N, remoteAndroidSetting as O, settingShapeErrors as P, PUBLIC_METRO_ENV as R, metroWarmupUrlSetting as S, projectOptimizations as T, optimizationBuildProfile as U, artifactCachePolicy as V, resolveOptimizations as W, iosSigningIdentitySha1SettingError as _, SETTING_SHAPE_REMEDY as a, metroIdleStopMinutesSetting as b, androidDataPartitionSizeBytes as c, cacheProviderSettingError as d, iosLanHostSetting as f, iosSigningIdentitySha1Setting as g, iosSigningIdentitySettingError as h, SETTINGS_WITH_RESOLVE_TIME_FALLBACK as i, resolveSettings as j, remoteIosSetting as k, androidDataPartitionSizeGbSetting as l, iosSigningIdentitySetting as m, PATH_SETTINGS as n, androidAvdConfigSetting as o, iosLanHostSettingError as p, REMOTE_DEVICE_BACKENDS as r, androidAvdConfigSettingError as s, ANDROID_AVD_CONFIG_HELP as t, androidDataPartitionSizeGbSettingError as u, iosSimSlimProfileSetting as v, projectMetroSharedCache as w, metroTunnelSettingError as x, mergeSettingsLayers as y, detectProviders as z };
@@ -1,8 +1,9 @@
1
- import { E as writeConfigSetting, T as withConfigLock, d as getConfigPath, g as loadConfig, j as isJsonObject, m as getRepoSettings, p as getProjectSettings } from "./config-Cp9lM3wX.mjs";
2
- import { _ as repoRoot, s as gitCommonDir } from "./worktree-R_cUlE7s.mjs";
3
- import { o as findProjectRoot, t as NO_PROJECT_REFUSAL } from "./project-DS112DYB.mjs";
4
- import { B as isSensitiveReference, F as unknownSettingKeys, H as settingValueError, R as SETTINGS, T as readCommittedSettings, V as settingDefinition, z as SETTING_SCOPES } from "./settings-D030k0t4.mjs";
1
+ import { E as writeConfigSetting, T as withConfigLock$1, d as getConfigPath$1, g as loadConfig$1, m as getRepoSettings, p as getProjectSettings } from "./config-BEq0Qw_a.mjs";
2
+ import { s as gitCommonDir, y as repoRoot } from "./worktree-BlizKDpZ.mjs";
3
+ import { o as findProjectRoot, t as NO_PROJECT_REFUSAL } from "./project-BXZzOABt.mjs";
4
+ import { D as readCommittedSettings, L as unknownSettingKeys } from "./settings-DOugPlPz.mjs";
5
5
  import { existsSync, readFileSync, renameSync, unlinkSync, writeFileSync } from "node:fs";
6
+ import { SETTINGS, SETTING_SCOPES, coerceSettingText, isJsonObject, isSensitiveReference, settingDefinition, settingValueError } from "@stim-cli/core/state";
6
7
  import { join } from "node:path";
7
8
  import chalk from "chalk";
8
9
  //#region src/commands/settings.ts
@@ -30,7 +31,7 @@ function readContext(env) {
30
31
  projectPath,
31
32
  gitCommonDir: common,
32
33
  repoRoot: common ? repoRoot(start) ?? projectPath : null,
33
- machine: loadConfig(),
34
+ machine: loadConfig$1(),
34
35
  env
35
36
  };
36
37
  }
@@ -52,7 +53,7 @@ function appDirectory(context) {
52
53
  return context.projectPath ?? context.repoRoot;
53
54
  }
54
55
  function layerFile(context, scope, setting) {
55
- const machineFile = getConfigPath();
56
+ const machineFile = getConfigPath$1();
56
57
  if (scope === "machine") return machineFile;
57
58
  if (scope === "workspace") return context.projectPath ? `${machineFile} (projects["${context.projectPath}"].settings)` : null;
58
59
  if (scope === "repo") return context.gitCommonDir ? `${machineFile} (repos["${context.gitCommonDir}"].settings)` : null;
@@ -85,7 +86,7 @@ function settingEntry(context, setting) {
85
86
  let value = null;
86
87
  let origin = null;
87
88
  if (env) {
88
- value = env.value;
89
+ value = masked(setting, envSettingValue(setting, envValue));
89
90
  origin = "env";
90
91
  } else if (scopedHome) {
91
92
  value = setting.scopedHomeValue;
@@ -191,24 +192,25 @@ function example(setting) {
191
192
  }
192
193
  function parseSettingValue(setting, raw) {
193
194
  const invalid = (expected) => new Refusal("STIM_BAD_ARG", `Invalid ${setting.key} value ${JSON.stringify(raw)}. Expected ${expected}.`, `For example: stim settings set ${setting.key} ${example(setting)}${setting.scopes.length > 1 ? ` --scope ${setting.scopes[0]}` : ""}`);
194
- let value = raw;
195
195
  const kind = setting.type.kind;
196
- if (kind === "boolean" || kind === "number" || kind === "strings" || kind === "object") try {
197
- value = JSON.parse(raw);
198
- } catch {
199
- value = raw;
200
- }
196
+ const value = coerceSettingText(setting, raw);
201
197
  const error = settingValueError(setting, value);
202
198
  if (error) throw invalid(kind === "strings" || kind === "object" ? `${error}, written as JSON` : error);
203
199
  return value;
204
200
  }
201
+ function envSettingValue(setting, raw) {
202
+ const value = coerceSettingText(setting, raw);
203
+ const error = settingValueError(setting, value);
204
+ if (error) throw new Refusal("STIM_BAD_ARG", `Invalid ${setting.env} value ${JSON.stringify(raw)}. Expected ${error}.`, `Fix the environment variable, or unset it and run \`stim settings set ${setting.key} ${example(setting)}\`.`);
205
+ return value;
206
+ }
205
207
  function committedTarget(context, setting) {
206
208
  const directory = committedDirectory(context, setting);
207
209
  if (!directory) throw new Refusal(NO_PROJECT_REFUSAL.code, NO_PROJECT_REFUSAL.message, NO_PROJECT_REFUSAL.remedy);
208
210
  return join(directory, ".stim.json");
209
211
  }
210
212
  function writeCommitted(file, key, value) {
211
- return withConfigLock(() => {
213
+ return withConfigLock$1(() => {
212
214
  const exists = existsSync(file);
213
215
  const text = exists ? readFileSync(file, "utf-8") : "";
214
216
  let parsed = {};