An AI API request should never be allowed to wait indefinitely.
Network problems, overloaded providers, or unexpectedly long generations can leave a request open much longer than your application should tolerate.
In JavaScript, AbortController provides a simple way to define a timeout and cancel the request.
A basic timeout wrapper
async function fetchWithTimeout(url, options = {}, timeoutMs = 15_000) {
const controller = new AbortController();
const timeoutId = setTimeout(() => {
controller.abort();
}, timeoutMs);
try {
return await fetch(url, {
...options,
signal: controller.signal,
});
} finally {
clearTimeout(timeoutId);
}
}
You can use it with an OpenAI-compatible endpoint:
const response = await fetchWithTimeout(
"https://your-api-endpoint/v1/chat/completions",
{
method: "POST",
headers: {
Authorization: `Bearer ${process.env.AI_API_KEY}`,
"Content-Type": "application/json",
},
body: JSON.stringify({
model: "your-model",
messages: [
{
role: "user",
content: "Explain exponential backoff in one paragraph.",
},
],
}),
},
30_000
);
Handle cancellation separately
An aborted request should not be treated like every other network failure:
try {
const response = await fetchWithTimeout(url, options, 30_000);
if (!response.ok) {
throw new Error(`HTTP ${response.status}`);
}
const data = await response.json();
console.log(data);
} catch (error) {
if (error.name === "AbortError") {
console.error("The AI request exceeded its timeout.");
} else {
console.error("The request failed:", error);
}
}
Separating AbortError makes it easier to log timeouts, display an appropriate message, and decide whether another attempt is safe.
Donβt retry blindly
A timeout and a retry solve different problems:
- A timeout prevents your application from waiting indefinitely.
- A retry creates a new request.
Automatically retrying an aborted request can duplicate work or produce unintended side effects. Before retrying, consider:
- Is the operation safe to repeat?
- Did the provider begin processing the original request?
- Could the request create or modify data?
- Is an idempotency key available?
- How many attempts have already been made?
- Should the retry use exponential backoff and jitter?
Retries should have a limit. They should also respect provider headers such as Retry-After when available.
Choose the timeout deliberately
There is no universal timeout value for every AI workload.
A short classification request may need a much lower limit than a long reasoning or generation task. Streaming responses may also need separate connection and inactivity timeouts.
Measure real production latency and choose limits based
Top comments (0)