@nomac/cli 0.13.0 → 0.13.1
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/package.json +1 -1
- package/src/mac-transport.mjs +13 -6
- package/src/session-ssh.mjs +2 -1
- package/src/ssh-config.mjs +1 -1
package/package.json
CHANGED
package/src/mac-transport.mjs
CHANGED
|
@@ -28,19 +28,26 @@ export function transportOptions(options = {}) {
|
|
|
28
28
|
return { url, token, agent: proxy ? new HttpsProxyAgent(proxy) : undefined, ca: options.ca };
|
|
29
29
|
}
|
|
30
30
|
|
|
31
|
-
/** How long a busy
|
|
32
|
-
export const GUEST_BUSY_RETRY = { budgetMs:
|
|
31
|
+
/** How long a busy or briefly unreachable Mac is retried before the error reaches the caller. */
|
|
32
|
+
export const GUEST_BUSY_RETRY = { budgetMs: 120_000, pauseMs: 3_000 };
|
|
33
|
+
/**
|
|
34
|
+
* Passing failures: a saturated guest (a first Simulator boot answers slowly for a minute or
|
|
35
|
+
* two), a Mac whose network dropped for a moment (most nights at its provider, October 2026),
|
|
36
|
+
* an answer lost on the way, or the same request still starting (copies of it that waited out
|
|
37
|
+
* an outage reach the Mac together).
|
|
38
|
+
*/
|
|
39
|
+
const PASSING = new Set(["guest_busy", "host_unavailable", "outcome_unknown", "operation_pending"]);
|
|
33
40
|
|
|
34
41
|
/**
|
|
35
|
-
*
|
|
36
|
-
*
|
|
37
|
-
*
|
|
42
|
+
* Guest operations are idempotent by job ID, request key and blob offset (a job start always
|
|
43
|
+
* carries its request key), so passing failures are retried with the same request; every other
|
|
44
|
+
* failure is returned for reconciliation.
|
|
38
45
|
*/
|
|
39
46
|
export function macRequest(method, path, options = {}) {
|
|
40
47
|
const started = Date.now();
|
|
41
48
|
// The first attempt runs synchronously, so invalid input still throws immediately.
|
|
42
49
|
const attempt = () => macRequestOnce(method, path, options).catch(async error => {
|
|
43
|
-
if (error?.code
|
|
50
|
+
if (!PASSING.has(error?.code) || Date.now() - started + GUEST_BUSY_RETRY.pauseMs + 15_000 > GUEST_BUSY_RETRY.budgetMs) throw error;
|
|
44
51
|
await new Promise(resolve => setTimeout(resolve, GUEST_BUSY_RETRY.pauseMs));
|
|
45
52
|
return attempt();
|
|
46
53
|
});
|
package/src/session-ssh.mjs
CHANGED
|
@@ -53,7 +53,8 @@ export function sshArgs(session, { batch = true } = {}) {
|
|
|
53
53
|
...(session.mode === "hosted" ? ["-F", "/dev/null", "-o", `UserKnownHostsFile=${session.knownHosts}`, "-o", "GlobalKnownHostsFile=/dev/null",
|
|
54
54
|
"-o", `HostKeyAlias=nomac-${session.id}`, "-o", `ProxyCommand=${[process.execPath, cliEntry(), "tunnel", session.id].map(shellQuote).join(" ")}`] : []),
|
|
55
55
|
"-o", "StrictHostKeyChecking=yes", "-o", "ForwardAgent=no",
|
|
56
|
-
|
|
56
|
+
// Two minutes of silence: a network drop at the Macs' provider pauses the stream until it resumes.
|
|
57
|
+
"-o", "ConnectTimeout=15", "-o", "ServerAliveInterval=15", "-o", "ServerAliveCountMax=8",
|
|
57
58
|
...multiplexArgs(session),
|
|
58
59
|
...(batch ? ["-o", "BatchMode=yes", "-o", "ClearAllForwardings=yes"] : []),
|
|
59
60
|
...(session.port ? ["-p", String(session.port)] : []),
|
package/src/ssh-config.mjs
CHANGED
|
@@ -52,7 +52,7 @@ export function sshConfigBlock(local, alias, project, { platform = process.platf
|
|
|
52
52
|
` ProxyCommand ${quoted(node)} ${quoted(bin)} tunnel ${local.id}`,
|
|
53
53
|
" ForwardAgent no",
|
|
54
54
|
" ServerAliveInterval 15",
|
|
55
|
-
" ServerAliveCountMax
|
|
55
|
+
" ServerAliveCountMax 8",
|
|
56
56
|
`${END} ${alias}`,
|
|
57
57
|
].join("\n");
|
|
58
58
|
}
|