(ctx: TestContext)
| 197 | // ═══════════════════════════════════════════════════════════════════════════ |
| 198 | |
| 199 | async function testClientTimeout(ctx: TestContext): Promise<void> { |
| 200 | console.log("\n═══ Test 3: Client Timeout ═══\n"); |
| 201 | |
| 202 | // Create a slow mock server |
| 203 | const slowServer = createServer((req, res) => { |
| 204 | // Never respond - let client timeout |
| 205 | req.on("data", () => {}); |
| 206 | req.on("end", () => { |
| 207 | // Don't send response - let it hang |
| 208 | }); |
| 209 | }); |
| 210 | |
| 211 | await new Promise<void>((resolve) => { |
| 212 | slowServer.listen(0, "127.0.0.1", () => resolve()); |
| 213 | }); |
| 214 | |
| 215 | const slowPort = (slowServer.address() as { port: number }).port; |
| 216 | |
| 217 | const slowProxy = await startProxy({ |
| 218 | wallet: TEST_WALLET, |
| 219 | apiBase: `http://127.0.0.1:${slowPort}`, |
| 220 | skipBalanceCheck: true, |
| 221 | requestTimeoutMs: 1000, // 1s timeout |
| 222 | }); |
| 223 | |
| 224 | try { |
| 225 | // Client with 500ms timeout (will timeout before proxy's 1s) |
| 226 | await fetch(`${slowProxy.baseUrl}/v1/chat/completions`, { |
| 227 | method: "POST", |
| 228 | headers: { "Content-Type": "application/json" }, |
| 229 | body: JSON.stringify({ |
| 230 | model: "deepseek/deepseek-chat", |
| 231 | messages: [{ role: "user", content: "test" }], |
| 232 | }), |
| 233 | signal: AbortSignal.timeout(500), |
| 234 | }).catch(() => {}); // Expected timeout |
| 235 | |
| 236 | // Wait for cleanup |
| 237 | await sleep(100); |
| 238 | |
| 239 | // Verify proxy recovered |
| 240 | const health = await fetch(`${slowProxy.baseUrl}/health`); |
| 241 | assert(health.ok, "Proxy survived client timeout"); |
| 242 | } catch (err) { |
| 243 | assert(false, `Timeout test failed: ${err instanceof Error ? err.message : String(err)}`); |
| 244 | } finally { |
| 245 | await slowProxy.close(); |
| 246 | await new Promise<void>((resolve) => slowServer.close(() => resolve())); |
| 247 | } |
| 248 | } |
| 249 | |
| 250 | // ═══════════════════════════════════════════════════════════════════════════ |
| 251 | // Test 4: Malformed HTTP (clientError Handler) |
no test coverage detected