@sjawhar/pi-legion-envoy 0.30.0 → 0.31.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/legion.js +44 -6
- package/package.json +1 -1
package/dist/legion.js
CHANGED
|
@@ -33279,6 +33279,36 @@ var exitProcess = (code) => process.exit(code);
|
|
|
33279
33279
|
function setLegionBootstrapExitForTests(hook) {
|
|
33280
33280
|
exitProcess = hook;
|
|
33281
33281
|
}
|
|
33282
|
+
var READY_RETRY_ATTEMPTS = 3;
|
|
33283
|
+
var READY_RETRY_DELAY_MS = 1000;
|
|
33284
|
+
function isNetworkOrTimeoutError(error) {
|
|
33285
|
+
if (!(error instanceof Error))
|
|
33286
|
+
return false;
|
|
33287
|
+
if (error.name === "NetworkError" || error.name === "TimeoutError")
|
|
33288
|
+
return true;
|
|
33289
|
+
const code = "code" in error && typeof error.code === "string" ? error.code : undefined;
|
|
33290
|
+
return code === "ConnectionRefused" || code === "ConnectionTimeout" || code === "EAI_AGAIN" || code === "ECONNREFUSED" || code === "ECONNRESET" || code === "EHOSTUNREACH" || code === "ENETUNREACH" || code === "ENOTFOUND" || code === "ETIMEDOUT" || error instanceof TypeError && (error.message === "Failed to fetch" || error.message === "fetch failed");
|
|
33291
|
+
}
|
|
33292
|
+
var callReadyWithRetry = async (label, call) => {
|
|
33293
|
+
for (let attempt = 1;attempt <= READY_RETRY_ATTEMPTS; attempt++) {
|
|
33294
|
+
try {
|
|
33295
|
+
await call();
|
|
33296
|
+
return;
|
|
33297
|
+
} catch (error) {
|
|
33298
|
+
const retryable = error instanceof LegionDaemonApiError ? error.status >= 500 && error.status < 600 : isNetworkOrTimeoutError(error);
|
|
33299
|
+
if (!retryable)
|
|
33300
|
+
throw error;
|
|
33301
|
+
if (attempt === READY_RETRY_ATTEMPTS) {
|
|
33302
|
+
console.error(`[legion] ${label} failed after ${attempt} attempts: ${messageFor(error)}`);
|
|
33303
|
+
throw error;
|
|
33304
|
+
}
|
|
33305
|
+
console.error(`[legion] ${label} failed (attempt ${attempt}/${READY_RETRY_ATTEMPTS}), retrying: ${messageFor(error)}`);
|
|
33306
|
+
const retryDelay = Promise.withResolvers();
|
|
33307
|
+
setTimeout(retryDelay.resolve, READY_RETRY_DELAY_MS);
|
|
33308
|
+
await retryDelay.promise;
|
|
33309
|
+
}
|
|
33310
|
+
}
|
|
33311
|
+
};
|
|
33282
33312
|
async function persistedTranscript(context) {
|
|
33283
33313
|
await context.sessionManager.ensureOnDisk();
|
|
33284
33314
|
const sessionFile = context.sessionManager.getSessionFile();
|
|
@@ -33453,15 +33483,19 @@ function legionExtension(pi) {
|
|
|
33453
33483
|
};
|
|
33454
33484
|
await claimEnvoyRole(sessionID, roleToken, context);
|
|
33455
33485
|
await startControlSubscription(sessionID);
|
|
33456
|
-
await roleDaemon().processReady({
|
|
33486
|
+
await callReadyWithRetry("root process/ready", () => roleDaemon().processReady({
|
|
33457
33487
|
tree,
|
|
33458
33488
|
sessionId: sessionID,
|
|
33459
33489
|
secret: started.secret
|
|
33460
|
-
});
|
|
33490
|
+
}));
|
|
33461
33491
|
registerArchitectTools();
|
|
33462
33492
|
await activateLegionTool();
|
|
33463
33493
|
} catch (error) {
|
|
33464
|
-
|
|
33494
|
+
if (error instanceof LegionDaemonApiError && (error.status === 401 || error.status === 403)) {
|
|
33495
|
+
console.error(`[legion] root bootstrap authorization failed after process/started registered a role; exiting so the daemon respawns a fresh attempt: ${messageFor(error)}`);
|
|
33496
|
+
} else {
|
|
33497
|
+
console.error(`[legion] root bootstrap failed after process/started registered a role; exiting so the daemon respawns a fresh attempt: ${messageFor(error)}`);
|
|
33498
|
+
}
|
|
33465
33499
|
exitProcess(1);
|
|
33466
33500
|
}
|
|
33467
33501
|
})();
|
|
@@ -33518,16 +33552,20 @@ function legionExtension(pi) {
|
|
|
33518
33552
|
registerArchitectTools();
|
|
33519
33553
|
await activateLegionTool();
|
|
33520
33554
|
}
|
|
33521
|
-
await roleDaemon().workerReady({
|
|
33555
|
+
await callReadyWithRetry("worker/ready", () => roleDaemon().workerReady({
|
|
33522
33556
|
tree,
|
|
33523
33557
|
issue,
|
|
33524
33558
|
role,
|
|
33525
33559
|
sessionId: sessionID,
|
|
33526
33560
|
secret: started.secret,
|
|
33527
33561
|
generation: generation(process.env)
|
|
33528
|
-
});
|
|
33562
|
+
}));
|
|
33529
33563
|
} catch (error) {
|
|
33530
|
-
|
|
33564
|
+
if (error instanceof LegionDaemonApiError && (error.status === 401 || error.status === 403)) {
|
|
33565
|
+
console.error(`[legion] worker bootstrap authorization failed after worker/started registered a role; exiting so the daemon respawns a fresh attempt: ${messageFor(error)}`);
|
|
33566
|
+
} else {
|
|
33567
|
+
console.error(`[legion] worker bootstrap failed after worker/started registered a role; exiting so the daemon respawns a fresh attempt: ${messageFor(error)}`);
|
|
33568
|
+
}
|
|
33531
33569
|
exitProcess(1);
|
|
33532
33570
|
}
|
|
33533
33571
|
})();
|