> ## Documentation Index
> Fetch the complete documentation index at: https://docs.trycurious.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Fallbacks and timeouts

> What a correct delivery path does when Curious is slow or down: a deadline on every decide, your control as the fallback, and no retries without a key.

A `decide` call sits in the path that renders your content. Curious is designed so that nothing on its side can break that path, but the guarantee is only as good as the client: every call needs a deadline and something to show when the deadline passes. The server SDK does both by default; this page is what it does, so you can do the same anywhere.

## The deadline

Pick a deadline you can afford in the render path and enforce it on the client. The server SDK's default is 1.5 seconds; the browser SDK's is 1 second, and lower is allowed. When it passes, abort the request and serve the fallback. A decision that arrives after you rendered is of no use to the user, and it still counts as a decision on our side, so do not wait for it.

## The fallback

The fallback is your control: the content you would show without Curious. It is the same thing you declared as `control`, which is why the SDK's `decide()` takes a required `fallback` and the browser SDK uses the page's own text. Serve it when:

* the deadline passes;
* the call fails with any status, including a `409` or a `5xx`;
* the response does not have the shape your renderer expects.

A user who sees the fallback sees your production content. The only cost is a decision that was not recorded, which is learning, not revenue.

## No retries without a key

A `decide` is a write: it records which arm the user saw, and a second decision for the same user and element ends the first one's window. A retry after a timeout or an ambiguous failure therefore risks a second decision. Either do not retry (the SDK's choice), or generate an `idempotency_key` before the first attempt and send the same key on the retry, which replays the original decision if it committed and makes a fresh one if it did not. See [Idempotency](https://docs.trycurious.ai/api-reference/idempotency.md).

## Where to call decide

Call `decide` on the server when you can: the key stays secret, the user's attributes are at hand, and the deadline competes with nothing else in the browser. Call it from the browser with a publishable key when the content is rendered client-side and the element is already declared. In both cases, call it once per exposure and reuse the result for that exposure; see [Assignment and stickiness](https://docs.trycurious.ai/concepts/assignment.md).

## Measure the fallback rate

Record how often you served the fallback and why. The SDK's result carries `served: "curious" | "fallback"`, `error.code` (`timeout`, `network_error`, `server_error`, `content_shape_mismatch`, …) and the `requestId` to quote to support. A rising fallback rate is the signal that a deadline is too tight for a cold runtime, that a key was revoked, or that the shape of a declared format and the renderer have drifted apart.

## With the server SDK

```ts theme={null}
const result = await curious.decide({
  element: "pricing_hero",
  userId: user.id,
  fallback: "Ship better experiments without manual analysis",
});

render(result.content);
if (result.served === "fallback") {
  logger.warn({ code: result.error?.code, requestId: result.requestId }, "curious fallback");
}
```

`decide()` never throws by default and never retries. Set `decideTimeoutMs` to change the deadline. See [Decide with the server SDK](https://docs.trycurious.ai/sdks/node/decide.md).

## Without an SDK

Use your HTTP client's timeout, catch every failure, and serve the control. The behaviours to reproduce are listed on [Raw HTTP](https://docs.trycurious.ai/sdks/http.md).

Next: the [go-live checklist](https://docs.trycurious.ai/guides/go-live.md). If the fallback keeps serving, see [The SDK keeps serving the fallback](https://docs.trycurious.ai/troubleshooting/fallback-served.md).


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.