stim 1.15.0 → 1.16.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.
- package/dist/{activity-B2-kb7k0.mjs → activity-BxwdD81S.mjs} +29 -16
- package/dist/agent-device-usage-output-Dpih1Tfa.mjs +411 -0
- package/dist/{android-Db2eEMaf.mjs → android-B_NumVyQ.mjs} +21 -20
- package/dist/{android-Cu_L4RpL.mjs → android-Ift4kVvt.mjs} +56 -47
- package/dist/{android-cas-PnKfAdB2.mjs → android-cas-8U4DPqeR.mjs} +1 -1
- package/dist/{android-CYmq0jNi.mjs → android-r2rBL8kV.mjs} +1 -1
- package/dist/{app-install-CAAplXAt.mjs → app-install-CKWdbXIX.mjs} +48 -5
- package/dist/attempt-Bk2ouQVL.mjs +39 -0
- package/dist/{budget-CMiqghig.mjs → budget-DjrURfQn.mjs} +356 -366
- package/dist/{build-plan-aeGMFX7e.mjs → build-plan-DjeSb2Xl.mjs} +19 -20
- package/dist/{build-slots-Df1ApSuH.mjs → build-slots-rUk77xqh.mjs} +7 -2
- package/dist/{cli-0cX5s4NM.mjs → cli-BkYZ_6hy.mjs} +23 -17
- package/dist/cli.mjs +1 -1
- package/dist/{client-C2IS36Qf.mjs → client-BTY686R6.mjs} +57 -22
- package/dist/collector-run.mjs +5 -192
- package/dist/{command-output-CliHHn7a.mjs → command-output-DnJMdEY-.mjs} +1 -1
- package/dist/{created-devices-BwVb3liH.mjs → created-devices-D5owjN4C.mjs} +1 -1
- package/dist/{dependency-state-BmsjKZ2H.mjs → dependency-state-B6cMXZab.mjs} +1 -1
- package/dist/{deps-BFlKbOIp.mjs → deps-urbmfXig.mjs} +2 -2
- package/dist/{dev-client-CjzLoNs0.mjs → dev-client-CroAIjjj.mjs} +3 -40
- package/dist/{device-BZ1IyS5A.mjs → device-DZQjF7H5.mjs} +7 -6
- package/dist/{device-capacity-DMuKC7nx.mjs → device-capacity-BHwxNBlu.mjs} +2 -2
- package/dist/device-host-worker.mjs +223 -28
- package/dist/{device-ios-DMQBUPus.mjs → device-ios-BadmeL2V.mjs} +7 -7
- package/dist/{device-lease-W5Pi1q38.mjs → device-lease-D-hLqx1b.mjs} +2 -2
- package/dist/{device-pool-B2r38YjS.mjs → device-lease-run-CqjShqWW.mjs} +5 -125
- package/dist/device-pool-CUaEWMMm.mjs +125 -0
- package/dist/{device-remote-9ulPsdhY.mjs → device-remote-D5WVWqOq.mjs} +12 -12
- package/dist/{doctor-BcE5xsBn.mjs → doctor-Cimf-gGB.mjs} +80 -34
- package/dist/{error-diagnostics-Cb0P1WLS.mjs → error-diagnostics-B9L4Ae0x.mjs} +11 -15
- package/dist/{gc-BuL1Genr.mjs → gc-Bqy4bjEu.mjs} +194 -31
- package/dist/{gradle-CmdOBq1d.mjs → gradle-BsO1MdsH.mjs} +4 -4
- package/dist/{guide-cCSGRFd3.mjs → guide-B_uyKTxW.mjs} +588 -53
- package/dist/{guide-status-CIoWK6mG.mjs → guide-status-CjEZMAD4.mjs} +1 -1
- package/dist/hosted-client-a-WmqE2L.mjs +197 -0
- package/dist/hosted-ios-CIWelIqf.mjs +220 -0
- package/dist/hosted-logs-D5g041Q3.mjs +187 -0
- package/dist/hosted-macos-BSZyIb3y.mjs +135 -0
- package/dist/{build-progress-C2Jv1AtA.mjs → idle-DYVymG92.mjs} +233 -6
- package/dist/{idle-shutdown-B5LPaNyY.mjs → idle-shutdown-CTsDnAde.mjs} +6 -6
- package/dist/{in-use-CndPMilN.mjs → in-use-DvBw0Kxo.mjs} +29 -9
- package/dist/{ios-3CtCRhwr.mjs → ios-BaInn3sW.mjs} +2 -2
- package/dist/ios-Cr1h5gnO.mjs +189 -0
- package/dist/{ios-Chob8ny7.mjs → ios-aq3QoGI3.mjs} +729 -452
- package/dist/{ios-device-DERmMmk-.mjs → ios-device-FfCN_C8p.mjs} +1 -1
- package/dist/ios-state-DS5UpYTH.mjs +48 -0
- package/dist/{launch-verify-CLlofxRt.mjs → launch-verify-2DBRizjo.mjs} +3 -3
- package/dist/logs-CHEVK8zD.mjs +371 -0
- package/dist/{machines-CYtOCqcj.mjs → machines-BIBUdhpj.mjs} +16 -10
- package/dist/{macos-BwtbUtTN.mjs → macos-CSYEAFmF.mjs} +22 -17
- package/dist/macos-run.mjs +1 -1
- package/dist/maintenance-run.d.mts +4 -0
- package/dist/maintenance-run.mjs +254 -0
- package/dist/{metro-Di8EN2Tb.mjs → metro-BeK1ZPz1.mjs} +1 -1
- package/dist/metro-gateway-BJ-rxQAB.mjs +84 -0
- package/dist/{named-ports-Dj_XBNaL.mjs → named-ports-Bk_YXEmE.mjs} +1 -1
- package/dist/{native-run-DFDoIRbY.mjs → native-run-NaBrRFtQ.mjs} +2 -2
- package/dist/{native-runtime-i6OkVg-w.mjs → native-runtime-DBzRnEKS.mjs} +6 -6
- package/dist/{ndjson-CDY9IkVC.mjs → ndjson-PclOIwVY.mjs} +2 -2
- package/dist/offload-worker.d.mts +1 -0
- package/dist/offload-worker.mjs +13 -8
- package/dist/{ownership-BkYxUtuj.mjs → ownership-DiA16AsN.mjs} +2 -2
- package/dist/{stop-cause-CZ_Mr-v9.mjs → ownership-hCkPzGmr.mjs} +4 -98
- package/dist/{ports-DddwttKM.mjs → ports-R2k4Knz3.mjs} +2 -2
- package/dist/{prebuild-BvxDlD6C.mjs → prebuild-D2fsca_Z.mjs} +4 -4
- package/dist/preview-DhVbvPAZ.mjs +318 -0
- package/dist/{project-CV3tDFHl.mjs → project-Du91Ilvc.mjs} +67 -3
- package/dist/{recordings-GEXp4iBT.mjs → recordings-BIXOzVnr.mjs} +1 -1
- package/dist/{reload-ChPiwvot.mjs → reload-rM9jV1fz.mjs} +49 -12
- package/dist/{remote-cache-CO2elm_b.mjs → remote-cache-C8-V13XN.mjs} +4 -4
- package/dist/{run-B-xqRrsg.mjs → run-f4vI6EnK.mjs} +2 -2
- package/dist/{server-bare-X7PUgizL.mjs → server-bare-CpPGmnmO.mjs} +1 -1
- package/dist/server-expo-CVqO2c35.mjs +2 -0
- package/dist/{server-expo-DhtX6bom.mjs → server-expo-MC0rHlOC.mjs} +4 -4
- package/dist/settings-BBpMcDbD.mjs +25 -0
- package/dist/{settings-DbL6uhH8.mjs → settings-ZkDzkzvB.mjs} +10 -4
- package/dist/settings-oTSkkNrM.mjs +1439 -0
- package/dist/settings.schema.json +432 -39
- package/dist/{simslim-Ciluxlq4.mjs → simslim-B8-7AoTI.mjs} +3 -3
- package/dist/{slot-launch-BY0BrOLh.mjs → slot-launch-B8VrHxn1.mjs} +10 -7
- package/dist/{spawn-entry-DncpJvWL.mjs → spawn-entry-jw19m8Nl.mjs} +1 -0
- package/dist/{start-CPO4wRg7.mjs → start-CX8Ig-U2.mjs} +1 -1
- package/dist/{start-CUD9nasA.mjs → start-ClDfwXa4.mjs} +21 -17
- package/dist/{state-BxCgeTQu.mjs → state-3DwSQIBK.mjs} +2 -2
- package/dist/{state-DFm77wRn.mjs → state-C1jB7Q8q.mjs} +5 -5
- package/dist/{state-CaeaHbDA.mjs → state-DcW6vOd_.mjs} +1 -1
- package/dist/{stats-DBLLFmKd.mjs → stats-CEZ_i5je.mjs} +16 -5
- package/dist/{status-l84Gbvp2.mjs → status-BuvBFeII.mjs} +5 -3
- package/dist/{status-DYXxNOT0.mjs → status-Cs7VLg9D.mjs} +148 -44
- package/dist/status-DlKvVJBE.mjs +49 -0
- package/dist/{stop-Bvf1MflS.mjs → stop-B0Yxtmiy.mjs} +3 -3
- package/dist/{stop-Bad61z_2.mjs → stop-Bffozsac.mjs} +61 -20
- package/dist/{stop-CceYh1yG.mjs → stop-Dt_dM16A.mjs} +2 -2
- package/dist/stop-cause-CidxIqup.mjs +97 -0
- package/dist/supervisor-run.mjs +148 -17
- package/dist/{support-CDQbDkL5.mjs → support-CAP8qDUF.mjs} +4 -3
- package/dist/{support-WLOzVKUv.mjs → support-D4aYJniO.mjs} +34 -9
- package/dist/{teardown-BYuQafiA.mjs → teardown-CL6vDs2Y.mjs} +56 -47
- package/dist/{toolchain-DmeYjXD9.mjs → toolchain-DkUflduf.mjs} +10 -10
- package/dist/trigger-Bemu8ytw.mjs +65 -0
- package/dist/trigger-CXts6qt1.mjs +2 -0
- package/dist/{warm-progress-DVHLN4uC.mjs → warm-progress-CpGv3Wb6.mjs} +274 -5
- package/dist/{web-k6w8-HnE.mjs → web-DWUaMp8P.mjs} +15 -16
- package/dist/web-run.mjs +5 -5
- package/dist/{workspace-state-CL2V2Ons.mjs → workspace-state-B8-aJ1_5.mjs} +33 -33
- package/dist/workspaces-BV4pdHFz.mjs +306 -0
- package/dist/{worktree-qXKzADSC.mjs → worktree-K-xj9Db0.mjs} +497 -30
- package/dist/{worktree-BT_uULFx.mjs → worktree-jnG8Iph5.mjs} +1 -1
- package/package.json +5 -5
- package/dist/hosted-macos-DwowNU7W.mjs +0 -447
- package/dist/logs-h9h6MUvE.mjs +0 -568
- package/dist/machine-usage-D_YYMzfR.mjs +0 -283
- package/dist/merge-state-BnxLNQiM.mjs +0 -272
- package/dist/server-expo-KJeD109I.mjs +0 -2
- package/dist/settings-CduVcoxj.mjs +0 -680
- package/dist/watchman-Bx0wceoF.mjs +0 -238
- package/dist/worktree-C0c5Udwa.mjs +0 -753
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
import { R as deviceSlotKey } from "./config-D0DbpZtM.mjs";
|
|
2
|
+
import { a as parseLease, f as selectPoolDevice, n as fileLeaseIo, r as leaseIsExpired, t as deviceLeasePath } from "./device-lease-D-hLqx1b.mjs";
|
|
3
|
+
import { i as DEVICE_WAIT_POLL_MS, n as DEVICE_BUSY, o as leaseExpiryText } from "./device-lease-run-CqjShqWW.mjs";
|
|
4
|
+
//#region src/engine/device-pool.ts
|
|
5
|
+
function heldPoolId(root, platform, now, io = fileLeaseIo, slot = "default") {
|
|
6
|
+
const record = io.readHolder(root)[deviceSlotKey(platform, slot)];
|
|
7
|
+
if (!record) return null;
|
|
8
|
+
const lease = parseLease(io.readLease(deviceLeasePath(platform, record.id)));
|
|
9
|
+
if (!lease || lease.token !== record.token || leaseIsExpired(lease, now)) return null;
|
|
10
|
+
return record.id;
|
|
11
|
+
}
|
|
12
|
+
function readPool(platform, candidates, io) {
|
|
13
|
+
const reading = {
|
|
14
|
+
usable: [],
|
|
15
|
+
leases: [],
|
|
16
|
+
unreadable: []
|
|
17
|
+
};
|
|
18
|
+
for (const candidate of candidates) {
|
|
19
|
+
const path = deviceLeasePath(platform, candidate.id);
|
|
20
|
+
const raw = io.readLease(path);
|
|
21
|
+
const lease = parseLease(raw);
|
|
22
|
+
if (raw !== null && !lease) {
|
|
23
|
+
reading.unreadable.push(path);
|
|
24
|
+
continue;
|
|
25
|
+
}
|
|
26
|
+
reading.usable.push(candidate);
|
|
27
|
+
if (lease) reading.leases.push(lease);
|
|
28
|
+
}
|
|
29
|
+
return reading;
|
|
30
|
+
}
|
|
31
|
+
function disconnectedHeldRefusal(id, idLabel) {
|
|
32
|
+
return {
|
|
33
|
+
code: "STIM_NO_DEVICE",
|
|
34
|
+
message: `This workspace leases ${id}, and it is not connected.`,
|
|
35
|
+
remedy: `Run \`stim device unlock\` to give it up, then run this command again. Naming another \`--device <${idLabel}>\` refuses the same way while this lease is held.`,
|
|
36
|
+
lease: null
|
|
37
|
+
};
|
|
38
|
+
}
|
|
39
|
+
const NO_LEASE_FACTS = {
|
|
40
|
+
platform: null,
|
|
41
|
+
id: null,
|
|
42
|
+
deviceName: null,
|
|
43
|
+
holder: null,
|
|
44
|
+
expiresAt: null
|
|
45
|
+
};
|
|
46
|
+
function unreadableSentence(unreadable) {
|
|
47
|
+
return unreadable.length ? ` Unreadable lease file, so no run may take that device around it: ${unreadable.join("; ")}.` : "";
|
|
48
|
+
}
|
|
49
|
+
function poolBusyRefusal(holders, leases, unreadable, now, waitSeconds, spare = [], idLabel = "id") {
|
|
50
|
+
const named = holders.map((holder) => `${holder.id} (${holder.holder}, until ${leaseExpiryText(holder.expiresAt, now)})`);
|
|
51
|
+
const first = holders[0];
|
|
52
|
+
const lease = first ? leases.find((entry) => entry.id === first.id) : void 0;
|
|
53
|
+
if (!first) return {
|
|
54
|
+
code: DEVICE_BUSY,
|
|
55
|
+
message: `Every connected device has an unreadable lease file, so Stim cannot tell who holds them: ${unreadable.join("; ")}.`,
|
|
56
|
+
remedy: "Read each file and, once you know no run depends on it, delete it. `stim gc` reports them on every run.",
|
|
57
|
+
lease: NO_LEASE_FACTS
|
|
58
|
+
};
|
|
59
|
+
return {
|
|
60
|
+
code: DEVICE_BUSY,
|
|
61
|
+
message: `Every connected device is leased by another workspace${waitSeconds > 0 ? `, and this run waited ${waitSeconds}s for one` : ""}: ${named.join("; ")}.${unreadableSentence(unreadable)}`,
|
|
62
|
+
remedy: (spare.length ? `Also connected and free: ${spare.join(", ")}. Name one with \`--device <${idLabel}>\` to use it now. ` : "") + "Wait longer with `--wait <seconds>`, connect another device, or pass `--no-wait` to install anyway -- which takes no lease and, when both workspaces build the same app id, terminates the holder's running app.",
|
|
63
|
+
lease: {
|
|
64
|
+
platform: lease?.platform ?? null,
|
|
65
|
+
id: first.id,
|
|
66
|
+
deviceName: lease?.deviceName ?? null,
|
|
67
|
+
holder: first.holder,
|
|
68
|
+
expiresAt: first.expiresAt
|
|
69
|
+
}
|
|
70
|
+
};
|
|
71
|
+
}
|
|
72
|
+
async function selectFromPool({ root, platform, slot = "default", idLabel, list, noCandidates, waitSeconds, deadline, noWait = false, now = Date.now, sleep = (ms) => new Promise((r) => setTimeout(r, ms)), warn = () => {}, io = fileLeaseIo }) {
|
|
73
|
+
const held = heldPoolId(root, platform, now(), io, slot);
|
|
74
|
+
const until = deadline ?? now() + waitSeconds * 1e3;
|
|
75
|
+
let lastLine = null;
|
|
76
|
+
for (;;) {
|
|
77
|
+
const { usable, leases, unreadable } = readPool(platform, list(), io);
|
|
78
|
+
const selection = selectPoolDevice({
|
|
79
|
+
candidates: usable,
|
|
80
|
+
leases,
|
|
81
|
+
held,
|
|
82
|
+
now: now()
|
|
83
|
+
});
|
|
84
|
+
if (selection.status === "selected") return selection;
|
|
85
|
+
if (selection.status === "held-disconnected") return {
|
|
86
|
+
status: "refused",
|
|
87
|
+
refusal: disconnectedHeldRefusal(selection.id, idLabel)
|
|
88
|
+
};
|
|
89
|
+
if (selection.status === "none") {
|
|
90
|
+
if (unreadable.length) return {
|
|
91
|
+
status: "refused",
|
|
92
|
+
refusal: poolBusyRefusal([], leases, unreadable, now(), waitSeconds)
|
|
93
|
+
};
|
|
94
|
+
const { message, remedy } = noCandidates();
|
|
95
|
+
return {
|
|
96
|
+
status: "refused",
|
|
97
|
+
refusal: {
|
|
98
|
+
code: "STIM_NO_DEVICE",
|
|
99
|
+
message,
|
|
100
|
+
remedy,
|
|
101
|
+
lease: null
|
|
102
|
+
}
|
|
103
|
+
};
|
|
104
|
+
}
|
|
105
|
+
const first = selection.holders[0];
|
|
106
|
+
if (noWait && first) {
|
|
107
|
+
const candidate = usable.find((entry) => entry.id === first.id);
|
|
108
|
+
if (candidate) return {
|
|
109
|
+
status: "selected",
|
|
110
|
+
candidate
|
|
111
|
+
};
|
|
112
|
+
}
|
|
113
|
+
if (now() >= until) return {
|
|
114
|
+
status: "refused",
|
|
115
|
+
refusal: poolBusyRefusal(selection.holders, leases, unreadable, now(), waitSeconds, selection.spare, idLabel)
|
|
116
|
+
};
|
|
117
|
+
if (lastLine === null || now() - lastLine >= 3e4) {
|
|
118
|
+
lastLine = now();
|
|
119
|
+
warn(`waiting for a free device; every connected one is leased: ${selection.holders.map((holder) => `${holder.id} (${holder.holder}, until ${leaseExpiryText(holder.expiresAt, now())})`).join("; ")}`);
|
|
120
|
+
}
|
|
121
|
+
await sleep(DEVICE_WAIT_POLL_MS);
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
//#endregion
|
|
125
|
+
export { selectFromPool as t };
|
|
@@ -1,18 +1,18 @@
|
|
|
1
1
|
import { t as getExecutor } from "./exec-CaErVv7t.mjs";
|
|
2
2
|
import { d as getConfigDir } from "./config-D0DbpZtM.mjs";
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
3
|
+
import { a as formatElapsed } from "./command-output-DnJMdEY-.mjs";
|
|
4
|
+
import { K as planMetroReach } from "./settings-oTSkkNrM.mjs";
|
|
5
|
+
import { l as ownedDeviceLabel } from "./project-Du91Ilvc.mjs";
|
|
6
|
+
import { o as pidExists } from "./metro-BeK1ZPz1.mjs";
|
|
7
|
+
import { C as workspaceStateFile, v as workspaceDir, w as withDirLock, x as workspaceLogsDir$1, y as workspaceId } from "./workspace-state-B8-aJ1_5.mjs";
|
|
8
|
+
import { a as clearRemoteSession, c as readMetroTunnel, u as readRemoteSession } from "./state-DcW6vOd_.mjs";
|
|
9
|
+
import { T as sanitizeDeviceLabel } from "./ios-BaInn3sW.mjs";
|
|
6
10
|
import { t as withWorkspaceProcessLock } from "./workspace-process-lock-BL7Q0HCO.mjs";
|
|
7
|
-
import {
|
|
8
|
-
import { o as
|
|
9
|
-
import {
|
|
10
|
-
import { T as sanitizeDeviceLabel } from "./ios-3CtCRhwr.mjs";
|
|
11
|
-
import { y as probePublicHttp } from "./stop-cause-CZ_Mr-v9.mjs";
|
|
12
|
-
import { i as INSTALL_ERROR, o as LAUNCH_ERROR, u as devClientDeepLink } from "./app-install-CAAplXAt.mjs";
|
|
13
|
-
import { c as readMetroRecords, o as isBundleProof } from "./launch-verify-CLlofxRt.mjs";
|
|
11
|
+
import { u as probePublicHttp } from "./ownership-hCkPzGmr.mjs";
|
|
12
|
+
import { i as INSTALL_ERROR, o as LAUNCH_ERROR, u as devClientDeepLink } from "./app-install-CKWdbXIX.mjs";
|
|
13
|
+
import { c as readMetroRecords, o as isBundleProof } from "./launch-verify-2DBRizjo.mjs";
|
|
14
14
|
import { t as compareStimVersions } from "./stim-installations-QMEI32v1.mjs";
|
|
15
|
-
import { c as nativeRunWaitNotice } from "./native-run-
|
|
15
|
+
import { c as nativeRunWaitNotice } from "./native-run-NaBrRFtQ.mjs";
|
|
16
16
|
import { existsSync, mkdirSync, realpathSync, renameSync, rmSync, writeFileSync } from "node:fs";
|
|
17
17
|
import { dirname, join, resolve } from "node:path";
|
|
18
18
|
import { easMachineStateRoot, easMachineStateRoot as easMachineStateRoot$1, easSessionLedgerFile, easSessionLedgerLock, readEasSessionLedger, readEasSessionLedger as readEasSessionLedger$1, readJsonObject, validEasSessionClaim } from "@stim-cli/core/state";
|
|
@@ -1293,7 +1293,7 @@ async function ensureMetroReachable({ ctx, metroPort, isExpo, tunnelMode = "auto
|
|
|
1293
1293
|
gate = recorded.provider !== "tailscale";
|
|
1294
1294
|
}
|
|
1295
1295
|
if (gate && resolvedUrl) {
|
|
1296
|
-
const logsDir = workspaceLogsDir(root);
|
|
1296
|
+
const logsDir = workspaceLogsDir$1(root);
|
|
1297
1297
|
const result = await gateOrigin({
|
|
1298
1298
|
origin: resolvedUrl,
|
|
1299
1299
|
metroPort,
|
|
@@ -1,36 +1,36 @@
|
|
|
1
1
|
import { t as getExecutor } from "./exec-CaErVv7t.mjs";
|
|
2
2
|
import { _ as loadConfig$1, p as getProject, s as configCorruptRepair, u as getConcurrencyLimits } from "./config-D0DbpZtM.mjs";
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
9
|
-
import {
|
|
10
|
-
import {
|
|
11
|
-
import {
|
|
3
|
+
import { d as quotedPath, f as refuseNoProject, l as phaseLine, u as plural } from "./command-output-DnJMdEY-.mjs";
|
|
4
|
+
import { B as settingsLayers, Ct as filesystemDevice, Et as temporaryRoot, H as unknownSettingKeys, I as settingOrigin, M as remoteIosSetting, O as projectOptimizations, P as resolveSettings, R as settingShapeErrors, U as webSettings, Y as compilerCacheFallbackMessage, Z as resolveOptimizations, a as SETTING_SHAPE_REMEDY, b as mergeSettingsLayers, dt as listWorktrees, ft as locallyKnownUpstream, gt as repoRoot, i as SETTINGS_WITH_RESOLVE_TIME_FALLBACK, it as gitCommonDir, j as remoteAndroidSetting, n as PATH_SETTINGS, nt as dirtyFingerprintFiles, vt as resolveSourceCheckout, wt as makeTemporaryDirectory, y as iosSimSlimProfileSetting } from "./settings-oTSkkNrM.mjs";
|
|
5
|
+
import { c as isPackageResolvable, n as appProjectProblem, o as findProjectRoot$1, r as detectIsExpo } from "./project-Du91Ilvc.mjs";
|
|
6
|
+
import { _ as workspaceDerivedData, d as sharedBuildCache } from "./workspace-state-B8-aJ1_5.mjs";
|
|
7
|
+
import { i as inspectBudget, n as budgetLine, z as inspectWatchmanMemory } from "./budget-DjrURfQn.mjs";
|
|
8
|
+
import { C as diffFingerprintSources, D as fingerprintProject, h as listBuildLocks } from "./device-lease-D-hLqx1b.mjs";
|
|
9
|
+
import { n as listBuildSlots } from "./build-slots-rUk77xqh.mjs";
|
|
10
|
+
import { D as hostSystemImageArch, O as listAdbDevices, ft as parkedMaxSetting, o as androidHome, ot as POOL_SETTING_REMEDY } from "./android-B_NumVyQ.mjs";
|
|
11
|
+
import { A as hostMemoryPressureAdvice, c as iosRuntimeMatches, j as readHostMemoryPressure, p as listIosRuntimes, u as listAllIosSims, y as pickDefaultIosCreation } from "./ios-BaInn3sW.mjs";
|
|
12
|
+
import { C as podInstallCommand, D as projectCmakeLauncher, S as bundlerPin, f as ccacheEnabled, i as macosToolchain, m as detectXcodeMajor, n as androidToolchain, r as iosToolchain, t as androidRequirements } from "./toolchain-DkUflduf.mjs";
|
|
13
|
+
import { b as realIo, h as inspectBuildMachines, o as offloadCheck, u as simulatorRuntime } from "./client-BTY686R6.mjs";
|
|
14
|
+
import { n as inspectDeviceHostMachines } from "./machines-BIBUdhpj.mjs";
|
|
12
15
|
import { a as findChrome, t as CHROME_INSTALL_REMEDY } from "./chrome-BrcVWQyD.mjs";
|
|
13
|
-
import { i as liveOwnedDeviceCount } from "./device-capacity-
|
|
14
|
-
import {
|
|
15
|
-
import { h as
|
|
16
|
-
import {
|
|
17
|
-
import {
|
|
18
|
-
import { m as resolveRuntime, p as resolveDeviceType } from "./support-WLOzVKUv.mjs";
|
|
19
|
-
import { f as resolveEasCliBin, i as checkEasAuth$1, l as ownerFromConfig, u as providerFromConfig } from "./remote-cache-CO2elm_b.mjs";
|
|
20
|
-
import { _ as easCliSupport, g as MIN_EAS_CLI_SIMULATOR_VERSION, s as readInstalledEasCliVersion, v as easCliUpgradeRemedy } from "./device-remote-9ulPsdhY.mjs";
|
|
16
|
+
import { i as liveOwnedDeviceCount } from "./device-capacity-BHwxNBlu.mjs";
|
|
17
|
+
import { d as androidPathRoomRemedy, l as androidPathRoom, n as apkOutputsDir, t as androidSdkRefusal, u as androidPathRoomMessage } from "./gradle-BsO1MdsH.mjs";
|
|
18
|
+
import { h as resolveRuntime, p as resolveDeviceType } from "./support-D4aYJniO.mjs";
|
|
19
|
+
import { f as resolveEasCliBin, i as checkEasAuth$1, l as ownerFromConfig, u as providerFromConfig } from "./remote-cache-C8-V13XN.mjs";
|
|
20
|
+
import { _ as easCliSupport, g as MIN_EAS_CLI_SIMULATOR_VERSION, s as readInstalledEasCliVersion, v as easCliUpgradeRemedy } from "./device-remote-D5WVWqOq.mjs";
|
|
21
21
|
import { n as inspectStimVersions, t as compareStimVersions } from "./stim-installations-QMEI32v1.mjs";
|
|
22
|
-
import { n as simslimIsOnPath, r as MIN_EAS_CLI_BUILD_DOWNLOAD_VERSION } from "./simslim-
|
|
23
|
-
import {
|
|
24
|
-
import { r as
|
|
25
|
-
import { n as recordDoctorRun } from "./guide-status-
|
|
26
|
-
import { n as hasInstalledDependencies, r as installedNpmTreeIsValid, t as dependencyState } from "./dependency-state-
|
|
22
|
+
import { n as simslimIsOnPath, r as MIN_EAS_CLI_BUILD_DOWNLOAD_VERSION } from "./simslim-B8-7AoTI.mjs";
|
|
23
|
+
import { r as resolveAndroidCompilerCache, t as readAndroidCasToolchain } from "./android-cas-8U4DPqeR.mjs";
|
|
24
|
+
import { r as maintenanceStatus, t as maintenanceLine } from "./status-DlKvVJBE.mjs";
|
|
25
|
+
import { n as recordDoctorRun } from "./guide-status-CjEZMAD4.mjs";
|
|
26
|
+
import { n as hasInstalledDependencies, r as installedNpmTreeIsValid, t as dependencyState } from "./dependency-state-B6cMXZab.mjs";
|
|
27
27
|
import { existsSync, lstatSync, readFileSync, readdirSync, realpathSync, rmSync } from "node:fs";
|
|
28
28
|
import { basename, dirname, isAbsolute, join, relative, resolve, sep } from "node:path";
|
|
29
29
|
import { existsSync as existsSync$1, lstatSync as lstatSync$1, mkdirSync as mkdirSync$1, readFileSync as readFileSync$1, readdirSync as readdirSync$1, realpathSync as realpathSync$1, renameSync as renameSync$1, rmSync as rmSync$1, writeFileSync as writeFileSync$1 } from "fs";
|
|
30
30
|
import { homedir } from "os";
|
|
31
31
|
import { dirname as dirname$1, isAbsolute as isAbsolute$1, join as join$1, relative as relative$1, resolve as resolve$1, sep as sep$1 } from "path";
|
|
32
32
|
import { InvalidArgumentError } from "commander";
|
|
33
|
-
import { isJsonObject, readHostedAppMetadata, readHostedSessions, readJsonObject, settingDefinition } from "@stim-cli/core/state";
|
|
33
|
+
import { isJsonObject, maintenanceNdjsonFile, readHostedAppMetadata, readHostedSessions, readJsonObject, readStats, settingDefinition } from "@stim-cli/core/state";
|
|
34
34
|
import chalk from "chalk";
|
|
35
35
|
import * as expoFingerprint from "@expo/fingerprint";
|
|
36
36
|
//#region src/diagnostics/sandbox.ts
|
|
@@ -662,6 +662,33 @@ function finding(level, title, detail, fix) {
|
|
|
662
662
|
fix
|
|
663
663
|
};
|
|
664
664
|
}
|
|
665
|
+
function checkOffloadCandidate(placements, machines, peers, now) {
|
|
666
|
+
if (machines.length || !peers.some((peer) => isJsonObject(peer) && peer.OS === "macOS" && peer.Online === true)) return null;
|
|
667
|
+
const cold = placements.filter((placement) => {
|
|
668
|
+
const age = now - Date.parse(placement.at);
|
|
669
|
+
return placement.decision === "here" && !placement.failed && (placement.buildMs ?? 0) > 0 && age >= 0 && age <= 6048e5;
|
|
670
|
+
});
|
|
671
|
+
if (cold.length < 3) return null;
|
|
672
|
+
const average = cold.reduce((total, placement) => total + placement.buildMs, 0) / cold.length;
|
|
673
|
+
if (average <= 18e4) return null;
|
|
674
|
+
return {
|
|
675
|
+
code: "offload-candidate",
|
|
676
|
+
...finding("note", "Builds could run on another Mac", `Cold builds averaged ~${Math.round(average / 6e4)} min over ${cold.length} builds this week.`, "In Stim Desktop, open Settings > Build machines > Add.")
|
|
677
|
+
};
|
|
678
|
+
}
|
|
679
|
+
function readOffloadCandidate(tailnetStatus, now, host) {
|
|
680
|
+
if (host !== "darwin") return null;
|
|
681
|
+
try {
|
|
682
|
+
const entries = loadConfig$1()?.offload?.machines;
|
|
683
|
+
const machines = Array.isArray(entries) ? entries.filter((entry) => typeof entry === "string") : [];
|
|
684
|
+
const placements = readStats().record?.placements ?? [];
|
|
685
|
+
if (machines.length || placements.length < 3) return null;
|
|
686
|
+
const status = tailnetStatus();
|
|
687
|
+
return checkOffloadCandidate(placements, machines, isJsonObject(status) && isJsonObject(status.Peer) ? Object.values(status.Peer) : [], now);
|
|
688
|
+
} catch {
|
|
689
|
+
return null;
|
|
690
|
+
}
|
|
691
|
+
}
|
|
665
692
|
function mainCheckoutProjectRoot(projectRoot) {
|
|
666
693
|
const currentRepoRoot = repoRoot(projectRoot);
|
|
667
694
|
if (!currentRepoRoot) return projectRoot;
|
|
@@ -969,7 +996,11 @@ function checkXcodeEnvLineEndings(projectRoot, platform, host) {
|
|
|
969
996
|
if (!content.includes("\r")) return null;
|
|
970
997
|
return finding("cost", "ios/.xcode.env has CRLF line endings", "An EAS build uploads the working-tree bytes of ios/.xcode.env, and Xcode sources that file with sh on the build worker, where each carriage return becomes part of the line and the build fails with `: command not found`. On Windows the usual cause is core.autocrlf=true rewriting the file at checkout.", "Run `git config core.autocrlf input` then `git checkout -- ios/.xcode.env`, or add `ios/.xcode.env text eol=lf` to .gitattributes and check the file out again.");
|
|
971
998
|
}
|
|
972
|
-
function
|
|
999
|
+
function configuredRemoteBackends(projectSettings, platform) {
|
|
1000
|
+
const iosTarget = remoteIosSetting(projectSettings);
|
|
1001
|
+
return [.../* @__PURE__ */ new Set([...platform !== "android" ? [iosTarget?.kind === "backend" ? iosTarget.backend : null] : [], ...platform !== "ios" ? [remoteAndroidSetting(projectSettings)] : []])].filter((backend) => backend !== null);
|
|
1002
|
+
}
|
|
1003
|
+
function runDoctor(projectRoot, { readFile = readFileSync$1, xcodeMajor = null, easAuth = checkEasAuth$1, concurrency = getConcurrencyLimits, liveDevices = null, activeBuilds = null, remoteEnv = process.env, lookupAgentDevice = null, lookupEasCli = null, lookupSimSlim = null, memoryPressure = readHostMemoryPressure, lookupCcache = null, lookupChrome, tailnetStatus = realIo.status, now = Date.now, platform, host = process.platform } = {}) {
|
|
973
1004
|
const localIos = platform !== "android" && host === "darwin";
|
|
974
1005
|
const read = (rel) => {
|
|
975
1006
|
const p = join$1(projectRoot, rel);
|
|
@@ -1045,7 +1076,7 @@ function runDoctor(projectRoot, { readFile = readFileSync$1, xcodeMajor = null,
|
|
|
1045
1076
|
profileError: simslimProfileError,
|
|
1046
1077
|
onPath: simslimProfile ? lookupSimSlim ? lookupSimSlim() : simslimIsOnPath() : false
|
|
1047
1078
|
});
|
|
1048
|
-
const remoteBackends =
|
|
1079
|
+
const remoteBackends = configuredRemoteBackends(projectSettings, platform);
|
|
1049
1080
|
const daemonInEnv = Boolean(remoteEnv.AGENT_DEVICE_DAEMON_BASE_URL?.trim() && remoteEnv.AGENT_DEVICE_DAEMON_AUTH_TOKEN?.trim());
|
|
1050
1081
|
const agentDeviceOnPath = remoteBackends.length ? lookupAgentDevice ? lookupAgentDevice() : agentDeviceIsOnPath() : false;
|
|
1051
1082
|
const easCliResolvable = remoteBackends.includes("eas") ? lookupEasCli ? lookupEasCli() : Boolean(resolveEasCliBin(projectRoot)) : false;
|
|
@@ -1085,6 +1116,7 @@ function runDoctor(projectRoot, { readFile = readFileSync$1, xcodeMajor = null,
|
|
|
1085
1116
|
easFinding,
|
|
1086
1117
|
easBuildDownloadFinding,
|
|
1087
1118
|
concurrencyFinding,
|
|
1119
|
+
readOffloadCandidate(tailnetStatus, now(), host),
|
|
1088
1120
|
memoryAdvice ? finding("cost", "Host memory pressure can stall the iOS simulator", memoryAdvice, "Free host memory, then retry. Run `stim guide lifecycle simslim` for the optional memory reduction setup.") : null,
|
|
1089
1121
|
simslimFinding,
|
|
1090
1122
|
...remoteFindings,
|
|
@@ -1338,15 +1370,15 @@ function hostedAgentDriverFinding(driver, apps) {
|
|
|
1338
1370
|
return {
|
|
1339
1371
|
code: "hosted-agent-driver",
|
|
1340
1372
|
level: "note",
|
|
1341
|
-
title: `${apps === 1 ? "A hosted
|
|
1342
|
-
detail: "The client's coding agent cannot drive these apps because `hosting.agentDriver` is none, so stim-server starts no driver. agent-device
|
|
1343
|
-
fix: "stim settings set hosting.agentDriver agent-device, with
|
|
1373
|
+
title: `${apps === 1 ? "A hosted app runs" : `${apps} hosted apps run`} with no agent driver`,
|
|
1374
|
+
detail: "The client's coding agent cannot drive these apps because `hosting.agentDriver` is none, so stim-server starts no driver. agent-device confines macOS control to one macos-app lease and iOS control to one simulator through its daemon policy.",
|
|
1375
|
+
fix: "stim settings set hosting.agentDriver agent-device, with agent-device 0.21.20 or later"
|
|
1344
1376
|
};
|
|
1345
1377
|
}
|
|
1346
|
-
function
|
|
1378
|
+
function runningHostedApps() {
|
|
1347
1379
|
try {
|
|
1348
1380
|
return readHostedSessions().filter((session) => {
|
|
1349
|
-
if (session.platform
|
|
1381
|
+
if (!["macos", "ios"].includes(session.platform) || session.state !== "ready" || !session.appAttempt) return false;
|
|
1350
1382
|
try {
|
|
1351
1383
|
return readHostedAppMetadata(session.id, session.appAttempt).state === "installed";
|
|
1352
1384
|
} catch {
|
|
@@ -1357,10 +1389,10 @@ function runningHostedMacosApps() {
|
|
|
1357
1389
|
return 0;
|
|
1358
1390
|
}
|
|
1359
1391
|
}
|
|
1360
|
-
/** Notes installed hosted macOS apps on this Mac while `hosting.agentDriver` starts no driver. */
|
|
1392
|
+
/** Notes installed hosted macOS and iOS apps on this Mac while `hosting.agentDriver` starts no driver. */
|
|
1361
1393
|
function inspectHostedAgentDriver() {
|
|
1362
1394
|
const hosting = loadConfig$1()?.hosting;
|
|
1363
|
-
return hostedAgentDriverFinding(isJsonObject(hosting) ? hosting.agentDriver : void 0,
|
|
1395
|
+
return hostedAgentDriverFinding(isJsonObject(hosting) ? hosting.agentDriver : void 0, runningHostedApps());
|
|
1364
1396
|
}
|
|
1365
1397
|
//#endregion
|
|
1366
1398
|
//#region src/commands/doctor.ts
|
|
@@ -1560,12 +1592,22 @@ function doctorCommand(program, version, inspectVersions = inspectStimVersions,
|
|
|
1560
1592
|
findings.push(...deviceHosts.findings);
|
|
1561
1593
|
const agentDriver = inspectHostedAgentDriver();
|
|
1562
1594
|
if (agentDriver) findings.push(agentDriver);
|
|
1595
|
+
const maintenance = maintenanceStatus();
|
|
1596
|
+
const maintenanceLines = [
|
|
1597
|
+
phaseLine("maintenance.mode", maintenance.mode),
|
|
1598
|
+
phaseLine("maintenance log", maintenanceNdjsonFile()),
|
|
1599
|
+
phaseLine("last pass", maintenanceLine(maintenance, false) ?? "no pass has run yet")
|
|
1600
|
+
];
|
|
1563
1601
|
if (opts.json) {
|
|
1564
1602
|
console.log(JSON.stringify({
|
|
1565
1603
|
project: root,
|
|
1566
1604
|
platform: opts.platform ?? null,
|
|
1567
1605
|
stim,
|
|
1568
1606
|
budget: budget.report,
|
|
1607
|
+
maintenance: {
|
|
1608
|
+
...maintenance,
|
|
1609
|
+
logPath: maintenanceNdjsonFile()
|
|
1610
|
+
},
|
|
1569
1611
|
buildMachines: buildMachines.machines,
|
|
1570
1612
|
deviceHosts: deviceHosts.machines,
|
|
1571
1613
|
findings
|
|
@@ -1574,7 +1616,7 @@ function doctorCommand(program, version, inspectVersions = inspectStimVersions,
|
|
|
1574
1616
|
return;
|
|
1575
1617
|
}
|
|
1576
1618
|
if (findings.length === 0) {
|
|
1577
|
-
const lines = doctorSuccessLines(opts.platform, stim, budget.report);
|
|
1619
|
+
const lines = [...doctorSuccessLines(opts.platform, stim, budget.report), ...maintenanceLines];
|
|
1578
1620
|
for (const [index, line] of lines.entries()) if (index === 1) console.log(chalk.green(line));
|
|
1579
1621
|
else if (line && !line.startsWith(" ")) console.log(chalk.bold(line));
|
|
1580
1622
|
else console.log(chalk.dim(line));
|
|
@@ -1583,7 +1625,11 @@ function doctorCommand(program, version, inspectVersions = inspectStimVersions,
|
|
|
1583
1625
|
}
|
|
1584
1626
|
const ordered = findings.toSorted((a, b) => a.level === b.level ? 0 : a.level === "cost" ? -1 : 1);
|
|
1585
1627
|
console.log(chalk.bold(`Doctor (${doctorTarget(opts.platform)})`));
|
|
1586
|
-
for (const line of [
|
|
1628
|
+
for (const line of [
|
|
1629
|
+
...stimVersionLines(stim),
|
|
1630
|
+
...budgetLines(budget.report),
|
|
1631
|
+
...maintenanceLines
|
|
1632
|
+
]) console.log(chalk.dim(line));
|
|
1587
1633
|
for (const f of ordered) {
|
|
1588
1634
|
const tag = f.level === "cost" ? chalk.yellow("costs time") : chalk.dim("note");
|
|
1589
1635
|
console.log(`\n${tag} ${chalk.bold(f.title)}`);
|
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
import { t as getExecutor } from "./exec-CaErVv7t.mjs";
|
|
2
2
|
import { R as deviceSlotKey, p as getProject, z as deviceSlotPlatforms } from "./config-D0DbpZtM.mjs";
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import { a as parseLease, n as fileLeaseIo, t as deviceLeasePath } from "./device-lease-
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
3
|
+
import { v as launchErrorPreview } from "./command-output-DnJMdEY-.mjs";
|
|
4
|
+
import { l as resolveProjectMetro } from "./metro-BeK1ZPz1.mjs";
|
|
5
|
+
import { r as readWorkspaceState$1, w as withDirLock } from "./workspace-state-B8-aJ1_5.mjs";
|
|
6
|
+
import { a as parseLease, n as fileLeaseIo, t as deviceLeasePath } from "./device-lease-D-hLqx1b.mjs";
|
|
7
|
+
import { f as readWorkspaceLaunches } from "./state-DcW6vOd_.mjs";
|
|
8
|
+
import { o as androidHome, u as androidToolCwd } from "./android-B_NumVyQ.mjs";
|
|
9
9
|
import { r as deviceConsoleLevel } from "./ios-device-Ee7sDXfp.mjs";
|
|
10
|
-
import { n as parseLogcatLine, t as androidClockOffset } from "./android-
|
|
10
|
+
import { n as parseLogcatLine, t as androidClockOffset } from "./android-r2rBL8kV.mjs";
|
|
11
11
|
import { createHash, randomUUID } from "node:crypto";
|
|
12
12
|
import { existsSync, mkdirSync, readFileSync, readdirSync, renameSync, statSync, unlinkSync, writeFileSync } from "node:fs";
|
|
13
13
|
import { basename, dirname, join, resolve, sep } from "node:path";
|
|
14
|
-
import { attachExpoErrorContext, readLogRecords,
|
|
14
|
+
import { NATIVE_CRASH_LOG_PREFIX, attachExpoErrorContext, readLogRecords, readLogTimeline } from "@stim-cli/core/state";
|
|
15
15
|
import { homedir } from "node:os";
|
|
16
16
|
//#region src/diagnostics/diagnostic-store.ts
|
|
17
17
|
/** Publishes an immutable diagnostic snapshot atomically; existing evidence wins. */
|
|
@@ -35,7 +35,6 @@ function writeDiagnosticOnce(path, content) {
|
|
|
35
35
|
}
|
|
36
36
|
//#endregion
|
|
37
37
|
//#region src/diagnostics/native-crash.ts
|
|
38
|
-
const CRASH_LOG_PREFIX = "native-crash-";
|
|
39
38
|
const IOS_CRASH_REPORT_RETRY = "iOS crash reports can take about a minute or longer to appear. Run `stim logs --errors` again for the native stack.";
|
|
40
39
|
/** Accepts only a report for this app, simulator and launch window. */
|
|
41
40
|
function parseIosCrash(text, target) {
|
|
@@ -347,7 +346,7 @@ function captureNativeCrashes(target, logsDir) {
|
|
|
347
346
|
record.incident ?? record.deviceTs,
|
|
348
347
|
record.rawReport
|
|
349
348
|
])).digest("hex");
|
|
350
|
-
writeDiagnosticOnce(join(logsDir, `${
|
|
349
|
+
writeDiagnosticOnce(join(logsDir, `${NATIVE_CRASH_LOG_PREFIX}${key}.ndjson`), `${JSON.stringify(record)}\n`);
|
|
351
350
|
} catch {}
|
|
352
351
|
}
|
|
353
352
|
return records;
|
|
@@ -358,7 +357,7 @@ function printNativeCrashReport(target, logsDir, emit, remote) {
|
|
|
358
357
|
}
|
|
359
358
|
/** Captures native crash reports for this workspace's current launches and returns the whole timeline. */
|
|
360
359
|
function captureWorkspaceCrashes(root, logsDir) {
|
|
361
|
-
const timeline = readLogRecords(logsDir, (name) => !
|
|
360
|
+
const timeline = readLogRecords(logsDir, (name) => !name.startsWith(NATIVE_CRASH_LOG_PREFIX));
|
|
362
361
|
const attempts = timeline.filter((record) => record.event === "launch_attempt");
|
|
363
362
|
const launches = readWorkspaceLaunches(root);
|
|
364
363
|
const latest = /* @__PURE__ */ new Map();
|
|
@@ -409,10 +408,7 @@ function captureWorkspaceCrashes(root, logsDir) {
|
|
|
409
408
|
}, logsDir);
|
|
410
409
|
} catch {}
|
|
411
410
|
}
|
|
412
|
-
return
|
|
413
|
-
}
|
|
414
|
-
function isCrashLog(name) {
|
|
415
|
-
return name.startsWith(CRASH_LOG_PREFIX);
|
|
411
|
+
return readLogTimeline(logsDir, timeline);
|
|
416
412
|
}
|
|
417
413
|
//#endregion
|
|
418
414
|
//#region src/diagnostics/error-symbolication.ts
|