Context
PR #5109 retired test/e2e/test-docker-unreachable-gateway-start.sh (originally protecting #2347 — the gateway-start fallback when Docker/Colima is unreachable). The replacement Vitest integration test at src/lib/onboard/gateway-start-failure-integration.test.ts covers everything reachable through already-exported helpers (printDockerDaemonRecovery, handleFinalGatewayStartFailure, reportLegacyGatewayStartResultFailure, classifyGatewayStartFailure) plus a composition test of the call-site sequence, but it leaves three caller-level contracts as it.todo placeholders because they cannot be proven without driving startGatewayWithOptions past its ~200 lines of preamble (gateway-reuse / ssh-keygen / known_hosts / docker-driver-detect).
What's missing
The three documented it.todo contracts in call-site contracts (caller-level coverage gap):
startGateway aborts via pRetry.AbortError without entering health-poll loop on docker-unreachable streamGatewayStart output
startGateway never invokes openshell statusorgateway info after docker-unreachable streamGatewayStart output
startGateway forwards dockerUnreachable=true to handleFinalGatewayStartFailure (no doctor logs collection, no destroyGateway cleanup) when streamGatewayStart returns docker-unreachable signature
Proposed fix
Extract the inner pRetry async body of startGatewayWithOptions (lines ~2310–2370 of src/lib/onboard.ts) into an exported helper that takes streamGatewayStart as a DI parameter, e.g.:
export async function attemptGatewayStart(
streamGatewayStartFn: typeof streamGatewayStart,
args: { command: string; env: NodeJS.ProcessEnv; healthPollCount: number; healthPollInterval: number; ... },
emitWaitingForHealth: () => void,
runStatusProbe: () => string,
runGatewayInfoProbe: (named: boolean) => string,
// ... other DI seams
): Promise<{ outcome: "healthy" | "unknown_failure"; dockerUnreachable: boolean }> { /* ... */ }
Then startGatewayWithOptions wraps attemptGatewayStart inside its existing try/catch + handleFinalGatewayStartFailure plumbing, and the test drives attemptGatewayStart directly with a mocked streamGatewayStartFn that returns the docker-unreachable signature.
Acceptance
- The three
it.todo entries in gateway-start-failure-integration.test.ts convert to real it() blocks and assert exactly what they claim.
startGatewayWithOptions behavior on main is unchanged (regression-test it the same way you'd test any refactor).
Refs
Context
PR #5109 retired
test/e2e/test-docker-unreachable-gateway-start.sh(originally protecting #2347 — the gateway-start fallback when Docker/Colima is unreachable). The replacement Vitest integration test atsrc/lib/onboard/gateway-start-failure-integration.test.tscovers everything reachable through already-exported helpers (printDockerDaemonRecovery,handleFinalGatewayStartFailure,reportLegacyGatewayStartResultFailure,classifyGatewayStartFailure) plus a composition test of the call-site sequence, but it leaves three caller-level contracts asit.todoplaceholders because they cannot be proven without drivingstartGatewayWithOptionspast its ~200 lines of preamble (gateway-reuse / ssh-keygen / known_hosts / docker-driver-detect).What's missing
The three documented
it.todocontracts incall-site contracts (caller-level coverage gap):startGateway aborts via pRetry.AbortError without entering health-poll loop on docker-unreachable streamGatewayStart outputstartGateway never invokes openshellstatusorgateway infoafter docker-unreachable streamGatewayStart outputstartGateway forwards dockerUnreachable=true to handleFinalGatewayStartFailure (no doctor logs collection, no destroyGateway cleanup) when streamGatewayStart returns docker-unreachable signatureProposed fix
Extract the inner
pRetryasync body ofstartGatewayWithOptions(lines ~2310–2370 ofsrc/lib/onboard.ts) into an exported helper that takesstreamGatewayStartas a DI parameter, e.g.:Then
startGatewayWithOptionswrapsattemptGatewayStartinside its existing try/catch +handleFinalGatewayStartFailureplumbing, and the test drivesattemptGatewayStartdirectly with a mockedstreamGatewayStartFnthat returns the docker-unreachable signature.Acceptance
it.todoentries ingateway-start-failure-integration.test.tsconvert to realit()blocks and assert exactly what they claim.startGatewayWithOptionsbehavior onmainis unchanged (regression-test it the same way you'd test any refactor).Refs