abhigyanpatwari/GitNexus · error · HttpEmbeddingError
Embedding request timed out after
Error message
Embedding request timed out after ${timeoutMs}ms (${safeUrl(url)}, batch ${batchIndex}) What it means
httpEmbedBatch maps a DOMException TimeoutError to this message: the per-request HTTP timeout (GITNEXUS_EMBEDDING_HTTP_TIMEOUT_MS, default 180000 ms, cap 300000 ms) expired while awaiting the endpoint. The abort signal wired to the body stream rejects with the timeout reason, which is preserved as the classification rather than being wrapped into a retryable body error.
Solutions
- Raise the timeout: export GITNEXUS_EMBEDDING_HTTP_TIMEOUT_MS=300000 (300s is the hard cap).
- Reduce batch size so each request completes faster.
- Warm up the model server (one manual curl) before running the pipeline.
- Move the endpoint closer / fix network latency; check server-side request logs for slow batches.
Example fix
# before (default 180s too short for cold model) # after export GITNEXUS_EMBEDDING_HTTP_TIMEOUT_MS=300000
Defensive patterns
Strategy: retry
Validate before calling
const timeoutMs = Number(process.env.GITNEXUS_EMBEDDING_HTTP_TIMEOUT_MS ?? 180_000);
const estimatedWorstBatchMs = texts.length * perTextBudgetMs;
if (estimatedWorstBatchMs > timeoutMs) {
process.env.GITNEXUS_EMBEDDING_HTTP_TIMEOUT_MS = '300000'; // or split the batch
} Type guard
const isEmbeddingTimeout = (e: unknown): boolean => e instanceof Error && /Embedding request timed out after \d+ms/.test(e.message);
Try / catch
try {
vectors = await httpEmbed(texts);
} catch (e) {
if (isEmbeddingTimeout(e)) {
const half = Math.ceil(texts.length / 2);
const [a, b] = [texts.slice(0, half), texts.slice(half)];
vectors = [...await httpEmbed(a), ...await httpEmbed(b)]; // smaller batches
} else throw e;
} Prevention
- Warm self-hosted model servers with a single-request curl before batch runs.
- Set GITNEXUS_EMBEDDING_HTTP_TIMEOUT_MS (≤300000) to a realistic p99 batch latency.
- Prefer smaller batches over bigger timeouts when the endpoint is cold or slow.
When it happens
Trigger: An embedding endpoint slower than the configured timeout for a given batch — cold-starting models, oversized batches, or network high latency — such that headers/body don't complete within timeoutMs.
Common situations: Self-hosted models (Ollama/llama.cpp) loading on first request, giant repositories producing large batches, CI runners with slow egress, default 180s exceeded only occasionally.
Understand the failure class
Background: Request timed out: what client-side request timeouts mean across libraries (Request timed out, TIMED_OUT, APITimeoutError) — this error's family across 39 libraries.
- Timeouts: ETIMEDOUT, deadlines, and hung requests — what actually expires when a request times out.
Related errors
- after attempt(s) ( , batch )
- Embedding endpoint circuit open
- Embedding endpoint returned an unexpected response shape
- Embedding endpoint returned an unparseable response
- Embedding endpoint returned
AI-assisted analysis of abhigyanpatwari/GitNexus@ac9a4e9abd (2026-08-20).
Data as JSON: /api/errors/fba250858298381c.
Report an issue: GitHub.
Appendix: source
Thrown at gitnexus/src/core/embeddings/http-client.ts:568
// carried, keeping the underlying parse error in `cause` only — the body
// text must never reach the `sanitizeReason` fallback and leak to stderr.
if (err instanceof RetryableEmbeddingBodyError) {
throw new HttpEmbeddingError(err.terminalMessage, { cause: err.cause });
}
if (err instanceof RetryableEmbeddingTimeoutError) {
throw new HttpEmbeddingError(
`${err.message} after ${maxAttempts} attempt(s) (${safeUrl(url)}, batch ${batchIndex})`,
{ cause: err.cause },
);
}
if (err instanceof CircuitOpenError) {
throw new HttpEmbeddingError(
`Embedding endpoint circuit open (${safeUrl(url)}, batch ${batchIndex}): retry in ${Math.ceil(err.retryAfterMs / 1000)}s`,
{ cause: err },
);
}
if (err instanceof DOMException && err.name === 'TimeoutError') {
throw new HttpEmbeddingError(
`Embedding request timed out after ${timeoutMs}ms (${safeUrl(url)}, batch ${batchIndex})`,
{ cause: err },
);
}
if (err instanceof ResilientFetchExhaustedError) {
throw new HttpEmbeddingError(
`Embedding endpoint returned ${err.response.status} (${safeUrl(url)}, batch ${batchIndex})`,
{ cause: err },
);
}
const reason = sanitizeReason(err instanceof Error ? err.message : String(err), url, apiKey);
const safeCause = new Error(reason);
safeCause.name = err instanceof Error ? err.name : 'EmbeddingTransportError';
throw new HttpEmbeddingError(
`Embedding request failed (${safeUrl(url)}, batch ${batchIndex}): ${reason}`,
{ cause: safeCause },
);
}View on GitHub (pinned to ac9a4e9abd)