(baseUrl: string, timeoutMs: number)
| 421 | } |
| 422 | |
| 423 | async function waitForHealth(baseUrl: string, timeoutMs: number): Promise<void> { |
| 424 | const deadline = Date.now() + timeoutMs; |
| 425 | const healthUrl = `${toHttpUrl(baseUrl)}/health`; |
| 426 | let lastError: unknown; |
| 427 | while (Date.now() < deadline) { |
| 428 | try { |
| 429 | const res = await fetch(healthUrl); |
| 430 | if (res.ok) return; |
| 431 | lastError = new Error(`HTTP ${res.status}`); |
| 432 | } catch (error) { |
| 433 | lastError = error; |
| 434 | } |
| 435 | await new Promise((resolve) => setTimeout(resolve, 250)); |
| 436 | } |
| 437 | throw new Error( |
| 438 | `${healthUrl} not healthy within ${timeoutMs}ms: ${lastError instanceof Error ? lastError.message : String(lastError)}`, |
| 439 | ); |
| 440 | } |
| 441 | |
| 442 | function toHttpUrl(input: string): string { |
| 443 | if (input.startsWith("ws://")) return `http://${input.slice("ws://".length)}`; |
no test coverage detected