stim 1.14.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/README.md +2 -0
- package/dist/activity-BxwdD81S.mjs +609 -0
- package/dist/agent-device-usage-output-Dpih1Tfa.mjs +411 -0
- package/dist/{android-d6rGq1pA.mjs → android-B_NumVyQ.mjs} +169 -81
- package/dist/{android-LbPFRWVL.mjs → android-Ift4kVvt.mjs} +517 -413
- package/dist/android-cas-8U4DPqeR.mjs +167 -0
- package/dist/android-cas-compiler.mjs +2 -2
- package/dist/{android-XpvCrV7q.mjs → android-r2rBL8kV.mjs} +2 -2
- package/dist/{app-install-BpgSgkJj.mjs → app-install-CKWdbXIX.mjs} +128 -151
- package/dist/attempt-Bk2ouQVL.mjs +39 -0
- package/dist/budget-DjrURfQn.mjs +2700 -0
- package/dist/{build-plan-Dcr-3ie0.mjs → build-plan-DjeSb2Xl.mjs} +192 -653
- package/dist/build-slots-rUk77xqh.mjs +132 -0
- package/dist/{cache-manifest-C68QQ0ua.mjs → cache-manifest-DnUHBJaU.mjs} +2 -2
- package/dist/cache-manifest.mjs +1 -1
- package/dist/{chrome-BPCiC3ZX.mjs → chrome-BrcVWQyD.mjs} +1 -1
- package/dist/cli-BkYZ_6hy.mjs +51 -0
- package/dist/cli.mjs +6 -42
- package/dist/client-BTY686R6.mjs +1368 -0
- package/dist/collector-run.mjs +9 -195
- package/dist/{command-output-DVcpw6eE.mjs → command-output-DnJMdEY-.mjs} +1 -1
- package/dist/{config-lvc7d3C2.mjs → config-D0DbpZtM.mjs} +28 -29
- package/dist/{created-devices-CllH_8eb.mjs → created-devices-D5owjN4C.mjs} +2 -2
- package/dist/{dependency-state-DsT7aKeo.mjs → dependency-state-B6cMXZab.mjs} +2 -2
- package/dist/{deps-D9IcKqXS.mjs → deps-urbmfXig.mjs} +3 -3
- package/dist/{detached-entry-DJHoca49.mjs → detached-entry-CiTEgMR1.mjs} +1 -1
- package/dist/dev-client-CroAIjjj.mjs +43 -0
- package/dist/{device-CjuuAJjQ.mjs → device-DZQjF7H5.mjs} +8 -7
- package/dist/device-capacity-BHwxNBlu.mjs +136 -0
- package/dist/device-host-worker.d.mts +1 -0
- package/dist/device-host-worker.mjs +964 -0
- package/dist/device-ios-BadmeL2V.mjs +381 -0
- package/dist/{device-lease-5c3WrVRm.mjs → device-lease-D-hLqx1b.mjs} +43 -36
- package/dist/{device-pool-BiyDyPP-.mjs → device-lease-run-CqjShqWW.mjs} +6 -126
- package/dist/device-pool-CUaEWMMm.mjs +125 -0
- package/dist/{device-remote-D87zEzaq.mjs → device-remote-D5WVWqOq.mjs} +69 -163
- package/dist/{doctor-x9pnU9fq.mjs → doctor-Cimf-gGB.mjs} +241 -103
- package/dist/{error-diagnostics-C5HzcwCW.mjs → error-diagnostics-B9L4Ae0x.mjs} +15 -18
- package/dist/{exec-DK8KaVHK.mjs → exec-CaErVv7t.mjs} +5 -1
- package/dist/{gc-ko6mUAYD.mjs → gc-Bqy4bjEu.mjs} +599 -108
- package/dist/{android-cas-iZK3DOCr.mjs → gradle-BsO1MdsH.mjs} +8 -294
- package/dist/{guide-6R0VNFqI.mjs → guide-B_uyKTxW.mjs} +2511 -239
- package/dist/{guide-status-BZrFPIA_.mjs → guide-status-CjEZMAD4.mjs} +3 -3
- 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/idle-DYVymG92.mjs +1099 -0
- package/dist/idle-shutdown-CTsDnAde.mjs +122 -0
- package/dist/in-use-DvBw0Kxo.mjs +130 -0
- package/dist/{ios-BwDPrnYQ.mjs → ios-BaInn3sW.mjs} +201 -10
- package/dist/ios-Cr1h5gnO.mjs +189 -0
- package/dist/{ios-P1f5nm2n.mjs → ios-aq3QoGI3.mjs} +1159 -633
- package/dist/{ios-device-BiOsSVzd.mjs → ios-device-Ee7sDXfp.mjs} +1 -1
- package/dist/{ios-device-DGglU3E_.mjs → ios-device-FfCN_C8p.mjs} +12 -7
- package/dist/ios-state-DS5UpYTH.mjs +48 -0
- package/dist/{launch-verify-Deg4tB3Z.mjs → launch-verify-2DBRizjo.mjs} +5 -5
- package/dist/logs-CHEVK8zD.mjs +371 -0
- package/dist/machines-BIBUdhpj.mjs +265 -0
- package/dist/macos-CSYEAFmF.mjs +473 -0
- package/dist/macos-run.d.mts +5 -0
- package/dist/macos-run.mjs +2 -0
- package/dist/maintenance-run.d.mts +4 -0
- package/dist/maintenance-run.mjs +254 -0
- package/dist/{metro-CcEo8Fl8.mjs → metro-BeK1ZPz1.mjs} +20 -120
- package/dist/metro-gateway-BJ-rxQAB.mjs +84 -0
- package/dist/{named-ports-Blg8IxOh.mjs → named-ports-Bk_YXEmE.mjs} +6 -59
- package/dist/native-run-NaBrRFtQ.mjs +147 -0
- package/dist/{native-runtime-DjBHRg5m.mjs → native-runtime-DBzRnEKS.mjs} +9 -5
- package/dist/{ndjson-CDY9IkVC.mjs → ndjson-PclOIwVY.mjs} +2 -2
- package/dist/offload-worker.d.mts +122 -0
- package/dist/offload-worker.mjs +606 -0
- package/dist/{ownership-DyYDF5ww.mjs → ownership-DiA16AsN.mjs} +3 -2
- package/dist/ownership-hCkPzGmr.mjs +571 -0
- package/dist/{page-BHUzTDFt.mjs → page-QF_Ke10s.mjs} +7 -2
- package/dist/{ports-BguS83ex.mjs → ports-R2k4Knz3.mjs} +3 -3
- package/dist/prebuild-D2fsca_Z.mjs +213 -0
- package/dist/preview-DhVbvPAZ.mjs +318 -0
- package/dist/process-identity-BmRm1qV0.mjs +12 -0
- package/dist/{project-CWlvEaeN.mjs → project-Du91Ilvc.mjs} +74 -19
- package/dist/pull-request-pxnDCQzn.mjs +322 -0
- package/dist/pull-requests.d.mts +120 -0
- package/dist/pull-requests.mjs +2 -0
- package/dist/recordings-BIXOzVnr.mjs +37 -0
- package/dist/{reload-BiniwsSZ.mjs → reload-rM9jV1fz.mjs} +109 -24
- package/dist/{remote-cache-CcR6o6lI.mjs → remote-cache-C8-V13XN.mjs} +5 -5
- package/dist/run-f4vI6EnK.mjs +119 -0
- package/dist/{server-bare-DGfgyJ5J.mjs → server-bare-CpPGmnmO.mjs} +33 -15
- package/dist/server-expo-CVqO2c35.mjs +2 -0
- package/dist/{server-expo-BVuwQ65v.mjs → server-expo-MC0rHlOC.mjs} +8 -12
- package/dist/settings-BBpMcDbD.mjs +25 -0
- package/dist/{settings-B-fsC-Om.mjs → settings-ZkDzkzvB.mjs} +22 -10
- package/dist/settings-oTSkkNrM.mjs +1439 -0
- package/dist/settings.schema.json +845 -97
- package/dist/{simslim-DrDN4WuV.mjs → simslim-B8-7AoTI.mjs} +8 -132
- package/dist/{slot-launch-D5t8EiMf.mjs → slot-launch-B8VrHxn1.mjs} +11 -8
- package/dist/{spawn-claims-Drw_o-Fb.mjs → spawn-claims-D0XfSe8u.mjs} +1 -1
- package/dist/spawn-entry-jw19m8Nl.mjs +17 -0
- package/dist/stage-CzaiwFsI.mjs +143 -0
- package/dist/start-CX8Ig-U2.mjs +2 -0
- package/dist/{start-s4RXp1wy.mjs → start-ClDfwXa4.mjs} +116 -65
- package/dist/state-3DwSQIBK.mjs +41 -0
- package/dist/state-B4PQFXMW.d.mts +12 -0
- package/dist/{state-Dk9RVXI7.mjs → state-C1jB7Q8q.mjs} +70 -8
- package/dist/{state-DHqvsbqC.mjs → state-DcW6vOd_.mjs} +7 -4
- package/dist/stats-CEZ_i5je.mjs +77 -0
- package/dist/{status-BgAuxESg.mjs → status-BuvBFeII.mjs} +118 -20
- package/dist/{status-BsPAnfOI.mjs → status-Cs7VLg9D.mjs} +542 -283
- package/dist/status-DlKvVJBE.mjs +49 -0
- package/dist/stdout-reader-C8yjre1x.mjs +23 -0
- package/dist/stim-desktop-Cnz8CPnl.mjs +63 -0
- package/dist/stim-footprint.swift +32 -0
- package/dist/{stim-installations-CINXy_su.mjs → stim-installations-QMEI32v1.mjs} +1 -1
- package/dist/stop-B0Yxtmiy.mjs +48 -0
- package/dist/{stop-BzreOWJp.mjs → stop-Bffozsac.mjs} +83 -16
- package/dist/{stop-BWIF_6BK.mjs → stop-Dt_dM16A.mjs} +2 -2
- package/dist/stop-cause-CidxIqup.mjs +97 -0
- package/dist/supervisor-run.d.mts +43 -11
- package/dist/supervisor-run.mjs +363 -24
- package/dist/support-CAP8qDUF.mjs +316 -0
- package/dist/support-D4aYJniO.mjs +201 -0
- package/dist/teardown-CL6vDs2Y.mjs +727 -0
- package/dist/{xcode-Cp5KvK9x.mjs → toolchain-DkUflduf.mjs} +364 -14
- package/dist/trigger-Bemu8ytw.mjs +65 -0
- package/dist/trigger-CXts6qt1.mjs +2 -0
- package/dist/warm-progress-CpGv3Wb6.mjs +732 -0
- package/dist/{web-BsQs1WlO.mjs → web-DWUaMp8P.mjs} +37 -21
- package/dist/web-run.mjs +310 -13
- package/dist/workspace-process-lock-BL7Q0HCO.mjs +57 -0
- package/dist/workspace-state-B8-aJ1_5.mjs +371 -0
- package/dist/workspaces-BV4pdHFz.mjs +306 -0
- package/dist/{worktree-UrQWXSeb.mjs → worktree-K-xj9Db0.mjs} +625 -256
- package/dist/worktree-jnG8Iph5.mjs +2 -0
- package/package.json +10 -5
- package/shim/bundle-response.cjs +28 -12
- package/dist/activity-CYVDcrt3.mjs +0 -356
- package/dist/budget-CGDkhvv_.mjs +0 -1745
- package/dist/build-progress-DxKpwnaS.mjs +0 -247
- package/dist/idle-DXtx3RbX.mjs +0 -191
- package/dist/in-use-DlqBDKqY.mjs +0 -249
- package/dist/logs-Civ4gbBH.mjs +0 -486
- package/dist/merge-state-ytFQCeh4.mjs +0 -262
- package/dist/server-expo-DIHDhvGg.mjs +0 -2
- package/dist/settings-D61iNOsB.mjs +0 -629
- package/dist/start-Cetfvy8l.mjs +0 -2
- package/dist/stats-CFpFGlJV.mjs +0 -62
- package/dist/stats-CX1Z8Tca.mjs +0 -368
- package/dist/stim-desktop-CXt8-Z3J.mjs +0 -40
- package/dist/stop-cause-hjGBOZTG.mjs +0 -1231
- package/dist/worktree-BVrHsYZG.mjs +0 -752
- package/dist/worktree-CHWWvm5v.mjs +0 -2
- package/dist/{metro-store-DzeWkfqW.mjs → metro-store-CDDZHtPl.mjs} +1 -1
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { t as resolveMaintenanceSettings } from "./settings-BBpMcDbD.mjs";
|
|
2
|
+
import { maintenanceRunClaims, readMaintenanceState } from "@stim-cli/core/state";
|
|
3
|
+
import { claimRemoveCommand, readClaimSet } from "@stim-cli/core/ownership-claim";
|
|
4
|
+
//#region src/maintenance/status.ts
|
|
5
|
+
function maintenanceStatus() {
|
|
6
|
+
const state = readMaintenanceState();
|
|
7
|
+
const claims = readClaimSet(maintenanceRunClaims());
|
|
8
|
+
const holder = claims.live[0];
|
|
9
|
+
const unresolved = claims.unresolved[0];
|
|
10
|
+
const settings = resolveMaintenanceSettings();
|
|
11
|
+
return {
|
|
12
|
+
mode: settings.mode,
|
|
13
|
+
...settings.invalid ? { invalid: settings.invalid } : {},
|
|
14
|
+
...unresolved ? { claim: {
|
|
15
|
+
unresolved: `${unresolved.path}: ${unresolved.reason}`,
|
|
16
|
+
removeCommand: claimRemoveCommand(unresolved.path)
|
|
17
|
+
} } : {},
|
|
18
|
+
lastChecks: {
|
|
19
|
+
pressure: state?.lastAt.pressure ?? null,
|
|
20
|
+
size: state?.lastAt.size ?? null
|
|
21
|
+
},
|
|
22
|
+
pressure: state?.pressure ?? null,
|
|
23
|
+
sizes: state?.sizes ?? [],
|
|
24
|
+
lastPass: state?.lastPass ?? null,
|
|
25
|
+
running: holder ? {
|
|
26
|
+
startedAt: holder.startedAt,
|
|
27
|
+
trigger: String(holder.details.trigger ?? "command")
|
|
28
|
+
} : null,
|
|
29
|
+
recent: state?.recent ?? [],
|
|
30
|
+
plan: state?.plan ?? []
|
|
31
|
+
};
|
|
32
|
+
}
|
|
33
|
+
function maintenanceLine(status, includeLabel = true) {
|
|
34
|
+
if (status.mode === "off" && !status.lastPass && !status.running && !status.invalid && !status.claim) return null;
|
|
35
|
+
const at = status.lastPass ? new Date(status.lastPass.startedAt).toLocaleTimeString("en-GB", {
|
|
36
|
+
hour: "2-digit",
|
|
37
|
+
minute: "2-digit"
|
|
38
|
+
}) : null;
|
|
39
|
+
const outputs = status.plan.filter((action) => action.kind === "would-clear-outputs");
|
|
40
|
+
const summary = outputs.length ? `would clear build outputs of ${outputs.length} ${outputs.length === 1 ? "workspace" : "workspaces"} (${(outputs.reduce((sum, action) => sum + action.bytes, 0) / 1024 ** 3).toFixed(1)} GB)` : `${status.plan.length} planned actions`;
|
|
41
|
+
const disk = status.pressure?.disk.map((volume) => `disk ${(volume.freeMb / 1024).toFixed(1)} GB free on ${volume.volume}`).join(", ");
|
|
42
|
+
return `${includeLabel ? `Auto maintenance (${status.mode === "report" ? "report only" : "off"}): ` : ""}${at ? `${at}: ` : ""}${status.lastPass ? summary : "no pass has run yet"}${disk ? `; ${disk}` : ""}${status.running ? "; running" : ""}${status.lastPass?.blocked.length ? `; ${status.lastPass.blocked.join("; ")}` : ""}${status.invalid ? `; invalid: ${status.invalid}` : ""}${status.claim ? `; unresolved claim: ${status.claim.unresolved}; ${status.claim.removeCommand}` : ""}`;
|
|
43
|
+
}
|
|
44
|
+
function maintenanceLines(status) {
|
|
45
|
+
const line = maintenanceLine(status);
|
|
46
|
+
return line === null ? [] : [line];
|
|
47
|
+
}
|
|
48
|
+
//#endregion
|
|
49
|
+
export { maintenanceLines as n, maintenanceStatus as r, maintenanceLine as t };
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { fstatSync } from "node:fs";
|
|
2
|
+
//#region src/stdout-reader.ts
|
|
3
|
+
const READER_CHECK_MS = 2e3;
|
|
4
|
+
/**
|
|
5
|
+
* Calls `onGone` once the process reading stdout is gone, for a streaming command that can stay quiet for a long
|
|
6
|
+
* time. Returns a function that stops watching.
|
|
7
|
+
*/
|
|
8
|
+
function watchStdoutReader(onGone) {
|
|
9
|
+
const parent = process.ppid;
|
|
10
|
+
const stdout = fstatSync(1);
|
|
11
|
+
const linuxPipe = process.platform === "linux" && (stdout.isFIFO() || stdout.isSocket());
|
|
12
|
+
const timer = setInterval(() => {
|
|
13
|
+
if (linuxPipe && process.ppid !== parent) onGone();
|
|
14
|
+
else process.stdout.write("");
|
|
15
|
+
}, READER_CHECK_MS);
|
|
16
|
+
process.stdout.on("error", onGone);
|
|
17
|
+
return () => {
|
|
18
|
+
clearInterval(timer);
|
|
19
|
+
process.stdout.off("error", onGone);
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
//#endregion
|
|
23
|
+
export { watchStdoutReader as t };
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import { t as getExecutor } from "./exec-CaErVv7t.mjs";
|
|
2
|
+
//#region src/devices/stim-desktop.ts
|
|
3
|
+
const LAUNCH_SERVICES_LOOKUP = `ObjC.import('AppKit'); const url = $.NSWorkspace.sharedWorkspace.URLForApplicationWithBundleIdentifier('dev.stim.desktop'); url.isNil() ? '' : url.path.js`;
|
|
4
|
+
const SCHEME_HANDLER_LOOKUP = `ObjC.import('AppKit'); const url = $.NSWorkspace.sharedWorkspace.URLForApplicationToOpenURL($.NSURL.URLWithString('stim-desktop://workspace')); url.isNil() ? '' : url.path.js`;
|
|
5
|
+
const STIM_DESKTOP_INSTALLED = "Stim Desktop installed";
|
|
6
|
+
/**
|
|
7
|
+
* macOS `open` passes its environment to an app it launches, so Stim Desktop
|
|
8
|
+
* started by a command run under a scoped `STIM_HOME` would serve that home.
|
|
9
|
+
*/
|
|
10
|
+
const STIM_DESKTOP_OPEN_OPTIONS = {
|
|
11
|
+
timeoutMs: 5e3,
|
|
12
|
+
killSignal: "SIGKILL",
|
|
13
|
+
omitEnv: ["STIM_HOME"]
|
|
14
|
+
};
|
|
15
|
+
/** Stim Desktop sets `STIM_DESKTOP_APP` to its bundle path for every command it runs; a non-empty value means Desktop is installed. */
|
|
16
|
+
function stimDesktopInstalled(platform = process.platform, env = process.env) {
|
|
17
|
+
if (platform !== "darwin") return false;
|
|
18
|
+
if (env.STIM_DESKTOP_APP) return true;
|
|
19
|
+
return launchServicesFinds(LAUNCH_SERVICES_LOOKUP);
|
|
20
|
+
}
|
|
21
|
+
function launchServicesFinds(script) {
|
|
22
|
+
return Boolean(getExecutor().runFileQuiet("osascript", [
|
|
23
|
+
"-l",
|
|
24
|
+
"JavaScript",
|
|
25
|
+
"-e",
|
|
26
|
+
script
|
|
27
|
+
], {
|
|
28
|
+
timeoutMs: 5e3,
|
|
29
|
+
killSignal: "SIGKILL"
|
|
30
|
+
}));
|
|
31
|
+
}
|
|
32
|
+
function stimDesktopHandlesLinks(platform = process.platform, env = process.env) {
|
|
33
|
+
if (platform !== "darwin") return false;
|
|
34
|
+
if (env.STIM_DESKTOP_APP) return true;
|
|
35
|
+
return launchServicesFinds(SCHEME_HANDLER_LOOKUP);
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* The links that open this workspace for a human, or undefined when no app on this Mac handles
|
|
39
|
+
* `stim-desktop://`. `target` names the device Stim Desktop focuses when the user opens the workspace.
|
|
40
|
+
*/
|
|
41
|
+
function workspaceLinks(root, target, handlesLinks = stimDesktopHandlesLinks) {
|
|
42
|
+
if (!handlesLinks()) return void 0;
|
|
43
|
+
let desktop = `stim-desktop://workspace?path=${linkParam(root)}`;
|
|
44
|
+
if (target) desktop += `&platform=${target.platform}`;
|
|
45
|
+
if (target?.slot && target.slot !== "default") desktop += `&slot=${linkParam(target.slot)}`;
|
|
46
|
+
return { desktop };
|
|
47
|
+
}
|
|
48
|
+
const linkParam = (value) => encodeURIComponent(value).replaceAll("%2F", "/");
|
|
49
|
+
function workspaceLinkLine(links) {
|
|
50
|
+
return `Open in Stim Desktop: ${links.desktop}`;
|
|
51
|
+
}
|
|
52
|
+
function settingDefault(setting, desktopInstalled = stimDesktopInstalled) {
|
|
53
|
+
if (setting.desktopDefault !== void 0 && desktopInstalled()) return {
|
|
54
|
+
value: setting.desktopDefault,
|
|
55
|
+
reason: STIM_DESKTOP_INSTALLED
|
|
56
|
+
};
|
|
57
|
+
return {
|
|
58
|
+
value: setting.default,
|
|
59
|
+
reason: null
|
|
60
|
+
};
|
|
61
|
+
}
|
|
62
|
+
//#endregion
|
|
63
|
+
export { workspaceLinks as a, workspaceLinkLine as i, settingDefault as n, stimDesktopInstalled as r, STIM_DESKTOP_OPEN_OPTIONS as t };
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
// Prints "<pid> <bytes>" for each pid, the pid's physical footprint: the value Activity Monitor's Memory column and
|
|
2
|
+
// top's MEM column show. With no arguments it reads every pid proc_listallpids(3) returns.
|
|
3
|
+
//
|
|
4
|
+
// The footprint comes from proc_pid_rusage(pid, RUSAGE_INFO_V4, ...) in <libproc.h>, field ri_phys_footprint of
|
|
5
|
+
// struct rusage_info_v4 in <sys/resource.h> (macOS 10.14+). The call fails with EPERM for another user's process
|
|
6
|
+
// unless the caller is root, and with ESRCH for a pid that has exited; those pids are left out of the output.
|
|
7
|
+
|
|
8
|
+
import Darwin
|
|
9
|
+
|
|
10
|
+
func allPids() -> [pid_t] {
|
|
11
|
+
var capacity = Int(proc_listallpids(nil, 0)) + 64
|
|
12
|
+
while true {
|
|
13
|
+
var pids = [pid_t](repeating: 0, count: capacity)
|
|
14
|
+
let count = pids.withUnsafeMutableBytes { proc_listallpids($0.baseAddress, Int32($0.count)) }
|
|
15
|
+
if count < 0 { return [] }
|
|
16
|
+
if Int(count) < capacity { return Array(pids.prefix(Int(count))) }
|
|
17
|
+
capacity *= 2
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
let arguments = CommandLine.arguments.dropFirst()
|
|
22
|
+
let pids = arguments.isEmpty ? allPids() : arguments.compactMap { pid_t($0) }
|
|
23
|
+
var output = ""
|
|
24
|
+
output.reserveCapacity(pids.count * 20)
|
|
25
|
+
var info = rusage_info_v4()
|
|
26
|
+
for pid in pids where pid > 0 {
|
|
27
|
+
let status = withUnsafeMutablePointer(to: &info) {
|
|
28
|
+
$0.withMemoryRebound(to: rusage_info_t?.self, capacity: 1) { proc_pid_rusage(pid, RUSAGE_INFO_V4, $0) }
|
|
29
|
+
}
|
|
30
|
+
if status == 0 { output += "\(pid) \(info.ri_phys_footprint)\n" }
|
|
31
|
+
}
|
|
32
|
+
fputs(output, stdout)
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { t as getExecutor } from "./exec-
|
|
1
|
+
import { t as getExecutor } from "./exec-CaErVv7t.mjs";
|
|
2
2
|
import { accessSync, constants, realpathSync, statSync } from "node:fs";
|
|
3
3
|
import { delimiter, join, resolve } from "node:path";
|
|
4
4
|
//#region src/diagnostics/stim-installations.ts
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import { n as ownership_claim_exports, t as process_identity_exports } from "./process-identity-BmRm1qV0.mjs";
|
|
2
|
+
import { c as writeWorkspaceState, v as workspaceDir } from "./workspace-state-B8-aJ1_5.mjs";
|
|
3
|
+
import { t as withWorkspaceProcessLock } from "./workspace-process-lock-BL7Q0HCO.mjs";
|
|
4
|
+
import { a as requiredMacosRecord, i as macosRuntimeClaim } from "./state-3DwSQIBK.mjs";
|
|
5
|
+
import { n as stopHostedMacos } from "./hosted-macos-BSZyIb3y.mjs";
|
|
6
|
+
import { readMacosRecord } from "@stim-cli/core/state";
|
|
7
|
+
//#region src/macos/stop.ts
|
|
8
|
+
async function stopProcess(record) {
|
|
9
|
+
if (!record) return;
|
|
10
|
+
for (const signal of ["SIGTERM", "SIGKILL"]) {
|
|
11
|
+
const identity = (0, process_identity_exports.inspectProcessIdentity)(record);
|
|
12
|
+
if (identity === "gone" || identity === "different") return;
|
|
13
|
+
if (identity !== "same") throw Object.assign(/* @__PURE__ */ new Error(`Cannot verify macOS owner pid ${record.pid}; no signal was sent.`), { code: "STIM_MACOS_OWNER_UNVERIFIED" });
|
|
14
|
+
process.kill(record.pid, signal);
|
|
15
|
+
if (await (0, process_identity_exports.waitForProcessExit)(record, 5e3)) return;
|
|
16
|
+
}
|
|
17
|
+
throw new Error(`Owned macOS process ${record.pid} did not exit.`);
|
|
18
|
+
}
|
|
19
|
+
async function stopMacosAppHeld(root) {
|
|
20
|
+
const record = requiredMacosRecord(root);
|
|
21
|
+
if (!record) return false;
|
|
22
|
+
await stopProcess(record.supervisor);
|
|
23
|
+
await stopProcess(readMacosRecord(root)?.app ?? record.app);
|
|
24
|
+
const claims = (0, ownership_claim_exports.readClaimSet)(macosRuntimeClaim(root));
|
|
25
|
+
if (claims.unresolved.length || claims.live.length) throw Object.assign(/* @__PURE__ */ new Error("The macOS runtime claim cannot be released; inspect its recorded owner before cleanup."), { code: "STIM_MACOS_OWNER_UNVERIFIED" });
|
|
26
|
+
return true;
|
|
27
|
+
}
|
|
28
|
+
/** Stops the workspace's app here, or its session on the hosting Mac, which must confirm the session stopped. */
|
|
29
|
+
function stopMacosApp(root) {
|
|
30
|
+
const stop = async () => {
|
|
31
|
+
const record = requiredMacosRecord(root);
|
|
32
|
+
if (!record?.host) return stopMacosAppHeld(root);
|
|
33
|
+
await stopHostedMacos(root, record.host);
|
|
34
|
+
const { host: _host, hostLaunched: _launched, ...stopped } = record;
|
|
35
|
+
writeWorkspaceState(root, { macos: {
|
|
36
|
+
...stopped,
|
|
37
|
+
supervisor: void 0
|
|
38
|
+
} });
|
|
39
|
+
return true;
|
|
40
|
+
};
|
|
41
|
+
return withWorkspaceProcessLock(workspaceDir(root), "macos-launch", stop, {
|
|
42
|
+
external: true,
|
|
43
|
+
waitMs: 0,
|
|
44
|
+
ownerPurpose: "stop macOS app"
|
|
45
|
+
});
|
|
46
|
+
}
|
|
47
|
+
//#endregion
|
|
48
|
+
export { stopMacosAppHeld as n, stopMacosApp as t };
|
|
@@ -1,23 +1,31 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import { a as
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import { n as fileLeaseIo, u as releaseWorkspaceLeases } from "./device-lease-
|
|
8
|
-
import {
|
|
9
|
-
import {
|
|
10
|
-
import {
|
|
11
|
-
import {
|
|
1
|
+
import { B as parseDeviceSlotKey, D as withConfigLock$1, E as upsertProject, H as projectDeviceSlots, V as parseDeviceSlotOption, W as validateDeviceSlot, o as clearSupervisor, p as getProject, z as deviceSlotPlatforms } from "./config-D0DbpZtM.mjs";
|
|
2
|
+
import { n as ownership_claim_exports, t as process_identity_exports } from "./process-identity-BmRm1qV0.mjs";
|
|
3
|
+
import { f as refuseNoProject, l as phaseLine, p as releasedLeaseFact, u as plural } from "./command-output-DnJMdEY-.mjs";
|
|
4
|
+
import { a as findCommandWorkspace } from "./project-Du91Ilvc.mjs";
|
|
5
|
+
import { l as resolveProjectMetro, o as pidExists, r as killMetroTree, u as signalProcessTree } from "./metro-BeK1ZPz1.mjs";
|
|
6
|
+
import { c as writeWorkspaceState, n as clearWorkspaceStateKeys, o as withWorkspaceStateLock, r as readWorkspaceState$1, v as workspaceDir } from "./workspace-state-B8-aJ1_5.mjs";
|
|
7
|
+
import { n as fileLeaseIo, u as releaseWorkspaceLeases } from "./device-lease-D-hLqx1b.mjs";
|
|
8
|
+
import { a as clearRemoteSession, c as readMetroTunnel, i as clearManagedMetroTunnel, o as clearWorkspaceLaunches, s as clearWorkspaceSupervisor, u as readRemoteSession } from "./state-DcW6vOd_.mjs";
|
|
9
|
+
import { a as teardownOwnedBrowser, i as teardownOwnedAvd, o as teardownOwnedIosSim } from "./teardown-CL6vDs2Y.mjs";
|
|
10
|
+
import { t as withWorkspaceProcessLock } from "./workspace-process-lock-BL7Q0HCO.mjs";
|
|
11
|
+
import { i as stopTunnel, t as resolveSupervisorTarget } from "./ownership-hCkPzGmr.mjs";
|
|
12
|
+
import { a as logVanishedSupervisor, l as withdrawDevServerStopRequest, s as requestDevServerStop } from "./stop-cause-CidxIqup.mjs";
|
|
13
|
+
import { n as verifyCollectorOwnership } from "./ownership-DiA16AsN.mjs";
|
|
14
|
+
import { t as stopMacosApp } from "./stop-B0Yxtmiy.mjs";
|
|
15
|
+
import { f as resolveEasCliBin } from "./remote-cache-C8-V13XN.mjs";
|
|
16
|
+
import { i as endRecordedSession } from "./device-remote-D5WVWqOq.mjs";
|
|
17
|
+
import { a as decideStopAction, c as nativeRunWaitNotice, i as clearNativeRunCancel, l as requestNativeRunCancel, n as NATIVE_RUN_WAIT_MS, o as describeNativeRunHolder, s as nativeRunHolder, t as NATIVE_RUN_LOCK } from "./native-run-NaBrRFtQ.mjs";
|
|
18
|
+
import { r as stopHostedIos } from "./hosted-ios-CIWelIqf.mjs";
|
|
19
|
+
import { hostedIosRecords, parseHostedIosPlacement } from "@stim-cli/core/state";
|
|
12
20
|
import chalk from "chalk";
|
|
13
21
|
//#region src/commands/stop.ts
|
|
14
22
|
const DEFAULT_WAIT_MS = 1e4;
|
|
15
23
|
function readSupervisorState(root) {
|
|
16
|
-
const sup = readWorkspaceState(root)?.supervisor;
|
|
24
|
+
const sup = readWorkspaceState$1(root)?.supervisor;
|
|
17
25
|
return sup && typeof sup === "object" ? sup : null;
|
|
18
26
|
}
|
|
19
27
|
function readCollectorState(root) {
|
|
20
|
-
const collectors = readWorkspaceState(root)?.collectors;
|
|
28
|
+
const collectors = readWorkspaceState$1(root)?.collectors;
|
|
21
29
|
return collectors && typeof collectors === "object" ? collectors : {};
|
|
22
30
|
}
|
|
23
31
|
function clearSupervisorState(root, expected) {
|
|
@@ -29,7 +37,7 @@ function clearSupervisorState(root, expected) {
|
|
|
29
37
|
}
|
|
30
38
|
function clearCollectorState(root, expected) {
|
|
31
39
|
return withWorkspaceStateLock(root, () => {
|
|
32
|
-
const current = { ...readWorkspaceState(root)?.collectors };
|
|
40
|
+
const current = { ...readWorkspaceState$1(root)?.collectors };
|
|
33
41
|
if (expected === void 0) {
|
|
34
42
|
clearWorkspaceStateKeys(root, ["collectors"]);
|
|
35
43
|
return true;
|
|
@@ -150,6 +158,8 @@ async function runStop(options) {
|
|
|
150
158
|
},
|
|
151
159
|
clearRegistration: async () => true,
|
|
152
160
|
teardownBrowser: null,
|
|
161
|
+
stopMacos: false,
|
|
162
|
+
hostedSlot: slot,
|
|
153
163
|
releaseLeases: (projectRoot) => releaseWorkspaceLeases(projectRoot, { slot })
|
|
154
164
|
});
|
|
155
165
|
result.outcomes.port = {
|
|
@@ -208,7 +218,52 @@ async function stopBrowserOnly({ root, project = void 0, teardownBrowser = (proj
|
|
|
208
218
|
summary: summarize(root, outcomes, ok)
|
|
209
219
|
};
|
|
210
220
|
}
|
|
211
|
-
async function
|
|
221
|
+
async function stopWorkspaceHostedIos(root, slot, report, failed) {
|
|
222
|
+
const devices = {};
|
|
223
|
+
let anyFailed = false;
|
|
224
|
+
for (const [name, record] of Object.entries(hostedIosRecords(readWorkspaceState$1(root)))) {
|
|
225
|
+
if (slot !== void 0 && name !== slot) continue;
|
|
226
|
+
const placement = parseHostedIosPlacement(record);
|
|
227
|
+
const label = placement ? `${placement.device?.name ?? "iOS simulator"} on ${placement.machine}` : `hosted iOS simulator for slot ${name}`;
|
|
228
|
+
try {
|
|
229
|
+
await stopHostedIos(root, name);
|
|
230
|
+
devices[`ios:host:${name}`] = {
|
|
231
|
+
status: "shut-down",
|
|
232
|
+
label
|
|
233
|
+
};
|
|
234
|
+
report(chalk.dim(phaseLine("device", `stopped ${label}`)));
|
|
235
|
+
} catch (error) {
|
|
236
|
+
const reason = error.message;
|
|
237
|
+
devices[`ios:host:${name}`] = {
|
|
238
|
+
status: "failed",
|
|
239
|
+
label,
|
|
240
|
+
reason
|
|
241
|
+
};
|
|
242
|
+
report(chalk.red(phaseLine("device", reason)));
|
|
243
|
+
failed();
|
|
244
|
+
anyFailed = true;
|
|
245
|
+
}
|
|
246
|
+
}
|
|
247
|
+
return {
|
|
248
|
+
devices,
|
|
249
|
+
failed: anyFailed
|
|
250
|
+
};
|
|
251
|
+
}
|
|
252
|
+
async function stopWorkspaceMacos(root, failed, enabled) {
|
|
253
|
+
if (enabled === false || readWorkspaceState$1(root)?.macos === void 0) return void 0;
|
|
254
|
+
try {
|
|
255
|
+
await stopMacosApp(root);
|
|
256
|
+
return { status: "stopped" };
|
|
257
|
+
} catch (error) {
|
|
258
|
+
const reason = error instanceof Error ? error.message : String(error);
|
|
259
|
+
failed(reason);
|
|
260
|
+
return {
|
|
261
|
+
status: "failed",
|
|
262
|
+
reason
|
|
263
|
+
};
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
async function stopWorkspace({ root, project = void 0, state = void 0, collectors = void 0, signalCollector = (pid) => signalProcessTree(pid), verifyCollector = verifyCollectorOwnership, clearCollectors = clearCollectorState, isAlive = pidExists, killGroup = killMetroTree, signalServer = (pid) => signalProcessTree(pid), inspectIdentity = process_identity_exports.inspectProcessIdentity, waitForDeath = void 0, waitMs = DEFAULT_WAIT_MS, resolveMetro = resolveProjectMetro, teardownIos = teardownOwnedIosSim, teardownAvd = teardownOwnedAvd, teardownBrowser = (projectRoot) => teardownOwnedBrowser(projectRoot), stopMacos, hostedSlot, remoteDevice = void 0, teardownRemoteSession = defaultTeardownRemoteSession, metroTunnel = void 0, stopMetroTunnel = stopTunnel, releaseLeases = releaseWorkspaceLeases, freePort = defaultFreePort, clearRegistration = defaultClearRegistration, clearState = clearSupervisorState, report = (line) => console.error(line) }) {
|
|
212
267
|
const proj = project === void 0 ? getProject(root) : project;
|
|
213
268
|
const sup = state === void 0 ? readSupervisorState(root) : state;
|
|
214
269
|
const collectorRecords = collectors === void 0 ? readCollectorState(root) : collectors;
|
|
@@ -365,6 +420,14 @@ async function stopWorkspace({ root, project = void 0, state = void 0, collector
|
|
|
365
420
|
}
|
|
366
421
|
outcomes.device.web = await closeBrowser(root, teardownBrowser, report);
|
|
367
422
|
if (outcomes.device.web && outcomes.device.web.status !== "shut-down") ok = false;
|
|
423
|
+
outcomes.macos = await stopWorkspaceMacos(root, (reason) => {
|
|
424
|
+
ok = false;
|
|
425
|
+
report(reason);
|
|
426
|
+
}, stopMacos);
|
|
427
|
+
const hosted = await stopWorkspaceHostedIos(root, hostedSlot, report, () => {
|
|
428
|
+
ok = false;
|
|
429
|
+
});
|
|
430
|
+
Object.assign(outcomes.device, hosted.devices);
|
|
368
431
|
const remote = remoteDevice === void 0 ? readRemoteSession(root) : remoteDevice;
|
|
369
432
|
const sessionId = typeof remote?.sessionId === "string" ? remote.sessionId : null;
|
|
370
433
|
if (sessionId) {
|
|
@@ -740,6 +803,8 @@ async function closeBrowser(root, teardownBrowser, report) {
|
|
|
740
803
|
}
|
|
741
804
|
function summarize(root, outcomes, ok) {
|
|
742
805
|
const parts = [];
|
|
806
|
+
if (outcomes.macos?.status === "stopped") parts.push("macOS app stopped");
|
|
807
|
+
if (outcomes.macos?.status === "failed") parts.push("macOS app could not be stopped");
|
|
743
808
|
if (outcomes.supervisor.status === "stopped") parts.push(`supervisor pid ${outcomes.supervisor.pid} stopped`);
|
|
744
809
|
if (outcomes.supervisor.status === "already-stopped") parts.push("supervisor already stopped");
|
|
745
810
|
if (outcomes.supervisor.status === "timeout") parts.push(`supervisor pid ${outcomes.supervisor.pid} still running`);
|
|
@@ -769,7 +834,7 @@ function summarize(root, outcomes, ok) {
|
|
|
769
834
|
return `${ok ? "Stopped" : "Stopped with problems"}: ${what} (${root})`;
|
|
770
835
|
}
|
|
771
836
|
function defaultFreePort(root, port) {
|
|
772
|
-
return withConfigLock(() => {
|
|
837
|
+
return withConfigLock$1(() => {
|
|
773
838
|
const current = getProject(root);
|
|
774
839
|
if (!current) return true;
|
|
775
840
|
if (current.supervisor || current.metroPort !== port) return false;
|
|
@@ -810,10 +875,12 @@ function recordedDeviceSlots(root) {
|
|
|
810
875
|
const parsed = parseDeviceSlotKey(key);
|
|
811
876
|
if (parsed) slots.add(parsed.slot);
|
|
812
877
|
}
|
|
878
|
+
for (const slot of Object.keys(hostedIosRecords(readWorkspaceState$1(root)))) slots.add(slot);
|
|
813
879
|
return [...slots].toSorted();
|
|
814
880
|
}
|
|
815
881
|
function workspaceDeviceSlots(root) {
|
|
816
882
|
const slots = projectDeviceSlots(getProject(root)).filter(({ platforms }) => Object.values(platforms).some(Boolean)).map(({ slot }) => slot);
|
|
883
|
+
for (const slot of Object.keys(hostedIosRecords(readWorkspaceState$1(root)))) if (!slots.includes(slot)) slots.push(slot);
|
|
817
884
|
if (typeof readRemoteSession(root)?.sessionId === "string" && !slots.includes("default")) slots.push("default");
|
|
818
885
|
return slots;
|
|
819
886
|
}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { a as resolveCollectorTargets, c as stopWorkspaceNow, i as readSupervisorState, n as clearSupervisorState, o as runStop, r as readCollectorState, s as stopCommand, t as clearCollectorState } from "./stop-
|
|
1
|
+
import { t as resolveSupervisorTarget } from "./ownership-hCkPzGmr.mjs";
|
|
2
|
+
import { a as resolveCollectorTargets, c as stopWorkspaceNow, i as readSupervisorState, n as clearSupervisorState, o as runStop, r as readCollectorState, s as stopCommand, t as clearCollectorState } from "./stop-Bffozsac.mjs";
|
|
3
3
|
export { clearCollectorState, clearSupervisorState, stopCommand as default, readCollectorState, readSupervisorState, resolveCollectorTargets, resolveSupervisorTarget, runStop, stopWorkspaceNow };
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
import { t as process_identity_exports } from "./process-identity-BmRm1qV0.mjs";
|
|
2
|
+
import { c as writeWorkspaceState, t as clearWorkspaceStateKey, x as workspaceLogsDir$1 } from "./workspace-state-B8-aJ1_5.mjs";
|
|
3
|
+
import { r as createNdjsonWriter } from "./ndjson-PclOIwVY.mjs";
|
|
4
|
+
import { join } from "node:path";
|
|
5
|
+
import { LOG_ROTATE_BYTES } from "@stim-cli/core";
|
|
6
|
+
import { DEV_SERVER_STOP_REQUEST_KEY, readDevServerStop, readDevServerStopRequest } from "@stim-cli/core/state";
|
|
7
|
+
//#region src/supervisor/stop-cause.ts
|
|
8
|
+
function requestDevServerStop(root, processToken, requester) {
|
|
9
|
+
if (!processToken) return;
|
|
10
|
+
try {
|
|
11
|
+
writeWorkspaceState(root, { [DEV_SERVER_STOP_REQUEST_KEY]: {
|
|
12
|
+
processToken,
|
|
13
|
+
by: requester.by,
|
|
14
|
+
pid: process.pid,
|
|
15
|
+
at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
16
|
+
...requester.workspace ? { workspace: requester.workspace } : {}
|
|
17
|
+
} });
|
|
18
|
+
} catch {}
|
|
19
|
+
}
|
|
20
|
+
function withdrawDevServerStopRequest(root, processToken) {
|
|
21
|
+
if (!processToken) return;
|
|
22
|
+
try {
|
|
23
|
+
clearWorkspaceStateKey(root, DEV_SERVER_STOP_REQUEST_KEY, (value) => {
|
|
24
|
+
return readDevServerStopRequest({ [DEV_SERVER_STOP_REQUEST_KEY]: value })?.processToken === processToken;
|
|
25
|
+
});
|
|
26
|
+
} catch {}
|
|
27
|
+
}
|
|
28
|
+
function devServerStopRecord(trigger, request, at) {
|
|
29
|
+
if (request) return {
|
|
30
|
+
reason: "requested",
|
|
31
|
+
at,
|
|
32
|
+
by: request.by,
|
|
33
|
+
byPid: request.pid,
|
|
34
|
+
...request.workspace ? { byWorkspace: request.workspace } : {}
|
|
35
|
+
};
|
|
36
|
+
return trigger.kind === "signal" ? {
|
|
37
|
+
reason: "signal",
|
|
38
|
+
at,
|
|
39
|
+
signal: trigger.signal
|
|
40
|
+
} : {
|
|
41
|
+
reason: "server-exited",
|
|
42
|
+
at,
|
|
43
|
+
mode: trigger.mode,
|
|
44
|
+
code: trigger.code,
|
|
45
|
+
signal: trigger.signal
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
function describeDevServerStop(record) {
|
|
49
|
+
if (record.reason === "idle") return `idle for ${record.idleMinutes} minutes (metro.idleStopMinutes)`;
|
|
50
|
+
if (record.reason === "requested") return `stop requested by ${record.by} (pid ${record.byPid}${record.byWorkspace ? ` in ${record.byWorkspace}` : ""})`;
|
|
51
|
+
if (record.reason === "signal") return `received ${record.signal} with no Stim stop request recorded, so it likely came from outside Stim`;
|
|
52
|
+
const detail = record.signal ? `signal ${record.signal}` : `exit code ${record.code ?? "unknown"}`;
|
|
53
|
+
const expoSignal = record.mode === "expo-child" && record.code === 0 ? "; Expo CLI also exits 0 on SIGTERM, and no Stim stop request was recorded" : "";
|
|
54
|
+
return `the ${record.mode} dev server exited unexpectedly (${detail})${expoSignal}`;
|
|
55
|
+
}
|
|
56
|
+
function devServerStopLevel(record) {
|
|
57
|
+
if (record.reason === "server-exited") return "error";
|
|
58
|
+
return record.reason === "signal" ? "warn" : "info";
|
|
59
|
+
}
|
|
60
|
+
/** The log line for a recorded supervisor whose process is proven gone, or null while it may still run. */
|
|
61
|
+
function vanishedSupervisorMessage(record) {
|
|
62
|
+
if (!record || typeof record.pid !== "number") return null;
|
|
63
|
+
const identity = (0, process_identity_exports.inspectProcessIdentity)(record);
|
|
64
|
+
if (identity !== "gone" && identity !== "different") return null;
|
|
65
|
+
const started = typeof record.startedAt === "string" ? ` (started ${record.startedAt})` : "";
|
|
66
|
+
return `supervisor pid ${record.pid}${started} ${VANISHED}`;
|
|
67
|
+
}
|
|
68
|
+
const VANISHED = "is gone and recorded no cause: usually SIGKILL, a crash or a machine restart";
|
|
69
|
+
function logVanishedSupervisor(root, record) {
|
|
70
|
+
const msg = vanishedSupervisorMessage(record);
|
|
71
|
+
if (!msg) return;
|
|
72
|
+
const writer = createNdjsonWriter(join(workspaceLogsDir$1(root), "metro.ndjson"), { maxBytes: LOG_ROTATE_BYTES });
|
|
73
|
+
writer.write({
|
|
74
|
+
src: "metro",
|
|
75
|
+
level: "warn",
|
|
76
|
+
event: "supervisor_vanished",
|
|
77
|
+
msg
|
|
78
|
+
});
|
|
79
|
+
writer.close();
|
|
80
|
+
}
|
|
81
|
+
/** The recorded stop, else a vanished supervisor when status proved the recorded one gone. */
|
|
82
|
+
function metroLastStop(state, supervisor) {
|
|
83
|
+
const recorded = readDevServerStop(state);
|
|
84
|
+
if (recorded) return recorded;
|
|
85
|
+
if (supervisor?.status !== "stale" || typeof supervisor.pid !== "number") return null;
|
|
86
|
+
const startedAt = typeof supervisor.startedAt === "string" ? supervisor.startedAt : null;
|
|
87
|
+
return {
|
|
88
|
+
reason: "vanished",
|
|
89
|
+
pid: supervisor.pid,
|
|
90
|
+
startedAt
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
function describeMetroLastStop(stop) {
|
|
94
|
+
return stop.reason === "vanished" ? `supervisor pid ${stop.pid} ${VANISHED}` : describeDevServerStop(stop);
|
|
95
|
+
}
|
|
96
|
+
//#endregion
|
|
97
|
+
export { logVanishedSupervisor as a, vanishedSupervisorMessage as c, devServerStopRecord as i, withdrawDevServerStopRequest as l, describeMetroLastStop as n, metroLastStop as o, devServerStopLevel as r, requestDevServerStop as s, describeDevServerStop as t };
|
|
@@ -1,19 +1,43 @@
|
|
|
1
1
|
import { t as NdjsonWriter } from "./ndjson-Du3j0AQ9.mjs";
|
|
2
|
-
import {
|
|
2
|
+
import { a as readPidFile, i as clearWorkspaceSupervisor, n as MODE_EXPO, o as writePidFile, r as clearExpoMetroTunnel, t as MODE_BARE } from "./state-B4PQFXMW.mjs";
|
|
3
|
+
import { DevServerStopRecord, DeviceActivity, IOS_SIMULATOR_APPS } from "@stim-cli/core/state";
|
|
3
4
|
//#region src/supervisor/idle-stop.d.ts
|
|
4
5
|
interface IdleProbe {
|
|
5
6
|
lastActivityAt(): number;
|
|
6
7
|
blocker(): string | null;
|
|
7
8
|
}
|
|
8
|
-
import * as import__stim_cli_core_process_identity from "@stim-cli/core/process-identity";
|
|
9
9
|
//#endregion
|
|
10
|
-
//#region src/
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
10
|
+
//#region src/commands/gc/idle.d.ts
|
|
11
|
+
interface OwnedDeviceActivity {
|
|
12
|
+
kind: "ios" | "android";
|
|
13
|
+
id: string;
|
|
14
|
+
name: string;
|
|
15
|
+
project: string;
|
|
16
|
+
slot: string;
|
|
17
|
+
activity: DeviceActivity;
|
|
18
|
+
}
|
|
19
|
+
//#endregion
|
|
20
|
+
//#region src/devices/idle-shutdown.d.ts
|
|
21
|
+
interface DueDevice {
|
|
22
|
+
device: OwnedDeviceActivity;
|
|
23
|
+
idleForMs: number;
|
|
24
|
+
}
|
|
25
|
+
/** The workspace's booted owned simulators and emulators that have been idle for `idleMs` or more. */
|
|
26
|
+
declare function dueIdleDevices(root: string, idleMs: number, now?: number): DueDevice[];
|
|
27
|
+
interface IdleShutdownEvent {
|
|
28
|
+
level: "info" | "warn";
|
|
29
|
+
event: "device_idle_shutdown" | "device_idle_shutdown_failed";
|
|
30
|
+
msg: string;
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Shuts down, through centralized teardown, each of the workspace's owned devices that is still idle for `idleMs`,
|
|
34
|
+
* and records why. The caller holds the workspace's native-run lock, so no `ios` or `android` run is booting or
|
|
35
|
+
* installing on them.
|
|
36
|
+
*/
|
|
37
|
+
declare function shutDownIdleDevices(root: string, idleMs: number, log: (event: IdleShutdownEvent) => void, now?: number): number;
|
|
38
|
+
//#endregion
|
|
39
|
+
//#region src/watchman.d.ts
|
|
40
|
+
type WatchmanCommand = (args: string[], timeoutMs: number) => Promise<unknown>;
|
|
17
41
|
//#endregion
|
|
18
42
|
//#region src/supervisor/run.d.ts
|
|
19
43
|
interface ParsedSupervisorArgs {
|
|
@@ -22,6 +46,7 @@ interface ParsedSupervisorArgs {
|
|
|
22
46
|
tunnel?: boolean;
|
|
23
47
|
resetCache?: boolean;
|
|
24
48
|
idleStopMinutes?: number;
|
|
49
|
+
deviceIdleMinutes?: number;
|
|
25
50
|
error?: string;
|
|
26
51
|
}
|
|
27
52
|
declare function parseArgs(argv: string[]): ParsedSupervisorArgs;
|
|
@@ -45,6 +70,10 @@ type ServerStarter = (opts: {
|
|
|
45
70
|
resetCache?: boolean;
|
|
46
71
|
onTunnelUrl?: ((url: string) => void) | null;
|
|
47
72
|
}) => Promise<ServerHandle>;
|
|
73
|
+
interface DeviceIdleOps {
|
|
74
|
+
due: typeof dueIdleDevices;
|
|
75
|
+
shutDown: typeof shutDownIdleDevices;
|
|
76
|
+
}
|
|
48
77
|
interface RunSupervisorOptions {
|
|
49
78
|
root: string;
|
|
50
79
|
port: number;
|
|
@@ -52,6 +81,8 @@ interface RunSupervisorOptions {
|
|
|
52
81
|
resetCache?: boolean;
|
|
53
82
|
idleStopMinutes?: number;
|
|
54
83
|
idleProbe?: IdleProbe;
|
|
84
|
+
deviceIdleMinutes?: number;
|
|
85
|
+
deviceIdle?: DeviceIdleOps;
|
|
55
86
|
isExpo?: (projectRoot: string) => boolean;
|
|
56
87
|
startBare?: ServerStarter | null;
|
|
57
88
|
startExpo?: ServerStarter | null;
|
|
@@ -59,8 +90,9 @@ interface RunSupervisorOptions {
|
|
|
59
90
|
onExit?: (code: number) => void;
|
|
60
91
|
attachSignals?: boolean;
|
|
61
92
|
stderr?: (line: string) => void;
|
|
93
|
+
watchman?: WatchmanCommand;
|
|
62
94
|
}
|
|
63
|
-
declare function runSupervisor({ root, port, tunnel, resetCache, idleStopMinutes, idleProbe, isExpo, startBare, startExpo, now, onExit, attachSignals, stderr }: RunSupervisorOptions): Promise<{
|
|
95
|
+
declare function runSupervisor({ root, port, tunnel, resetCache, idleStopMinutes, idleProbe, deviceIdleMinutes, deviceIdle, isExpo, startBare, startExpo, now, onExit, attachSignals, stderr, watchman }: RunSupervisorOptions): Promise<{
|
|
64
96
|
mode: string;
|
|
65
97
|
server: ServerHandle | undefined;
|
|
66
98
|
shutdown: (code: number, event: string, msg: string, stop?: DevServerStopRecord) => Promise<void>;
|
|
@@ -68,4 +100,4 @@ declare function runSupervisor({ root, port, tunnel, resetCache, idleStopMinutes
|
|
|
68
100
|
} | null>;
|
|
69
101
|
declare function main(argv?: string[]): Promise<void>;
|
|
70
102
|
//#endregion
|
|
71
|
-
export { MODE_BARE, MODE_EXPO, RunSupervisorOptions, ServerExitInfo, ServerHandle, clearExpoMetroTunnel, clearWorkspaceSupervisor, main, parseArgs, readPidFile, runSupervisor, writePidFile };
|
|
103
|
+
export { DeviceIdleOps, MODE_BARE, MODE_EXPO, RunSupervisorOptions, ServerExitInfo, ServerHandle, clearExpoMetroTunnel, clearWorkspaceSupervisor, main, parseArgs, readPidFile, runSupervisor, writePidFile };
|