fix(onboard): clamp gateway reachability polling

This commit is contained in:
Peter Steinberger
2026-05-30 19:28:06 -04:00
parent 5de0d873ed
commit bb680a845b
2 changed files with 33 additions and 2 deletions

View File

@@ -16,6 +16,7 @@ import {
resolveControlUiLinks,
summarizeExistingConfig,
validateGatewayPasswordInput,
waitForGatewayReachable,
} from "./onboard-helpers.js";
const mocks = vi.hoisted(() => ({
@@ -307,6 +308,31 @@ describe("probeGatewayReachable", () => {
});
});
describe("waitForGatewayReachable", () => {
it("keeps oversized poll intervals within the overall deadline", async () => {
mocks.probeGateway.mockResolvedValue({
ok: false,
url: "ws://127.0.0.1:18789",
connectLatencyMs: null,
error: "connect failed: timeout",
close: null,
health: null,
status: null,
presence: null,
configSnapshot: null,
});
const result = await waitForGatewayReachable({
url: "ws://127.0.0.1:18789",
deadlineMs: 5,
pollMs: Number.MAX_SAFE_INTEGER,
probeTimeoutMs: 1,
});
expect(result).toEqual({ ok: false, detail: "connect failed: timeout" });
});
});
describe("summarizeExistingConfig", () => {
it("collapses gateway fields into a friendly remote summary", () => {
expect(

View File

@@ -2,6 +2,7 @@ import fs from "node:fs/promises";
import path from "node:path";
import { inspect } from "node:util";
import { cancel, isCancel } from "@clack/prompts";
import { resolveTimerTimeoutMs } from "@openclaw/normalization-core/number-coercion";
import { normalizeOptionalString } from "@openclaw/normalization-core/string-coerce";
import { uniqueStrings } from "@openclaw/normalization-core/string-normalization";
import { visibleWidth } from "../../packages/terminal-core/src/ansi.js";
@@ -339,7 +340,7 @@ export async function waitForGatewayReachable(params: {
pollMs?: number;
}): Promise<{ ok: boolean; detail?: string }> {
const deadlineMs = params.deadlineMs ?? 15_000;
const pollMs = params.pollMs ?? 400;
const pollMs = resolveTimerTimeoutMs(params.pollMs ?? 400, 400, 0);
const probeTimeoutMs = params.probeTimeoutMs ?? 1500;
const startedAt = Date.now();
let lastDetail: string | undefined;
@@ -355,7 +356,11 @@ export async function waitForGatewayReachable(params: {
return probe;
}
lastDetail = probe.detail;
await sleep(pollMs);
const remainingMs = deadlineMs - (Date.now() - startedAt);
if (remainingMs <= 0) {
break;
}
await sleep(Math.min(pollMs, remainingMs));
}
return { ok: false, detail: lastDetail };