PerdurancePerdurance

Durable LLM requests

The connection drops.
The request doesn’t.

Submit an LLM request and get an id back immediately. Perdurance runs the upstream call, stores every chunk as it arrives, and hands you the result whenever you come back — whole, or as a stream replayed from the beginning.

Works through your provider’s existing SDK. No client changes.

streaming

0 / 0 chunks deliveredbilled once

A running example. The socket closes mid-stream, then reconnects and replays everything produced while it was gone.

Streams survive disconnects

A closed socket loses nothing. Reconnect and the stream replays from where you stopped, or from the first chunk. Tail it live, or collect it tomorrow.

The failures this covers

Retries never double-bill

Re-sending the same body inside the idempotency window attaches to the execution already running rather than starting a second one. Your provider is paid once.

How the retry is made safe

Every request is a record

The request, the response, each chunk and the usage counts are stored and queryable by id — per key, per model, for as long as you keep them.

What a record holds

How it works

Three calls, and none of them hold a connection open.

  1. 01

    Submit

    POST your request body to your provider’s own route, in your provider’s own dialect. You get 202 and a request id straight back — no socket held open.

    POST /v1/chat/completions
    202 Accepted
    { "id": "req_8f3a2c91" }
  2. 02

    Execute

    The upstream call runs server-side. Every chunk is persisted as it arrives, whether or not anything is listening for it.

    chunk 001  stored
    chunk 002  stored
    …
    client disconnected — still storing
  3. 03

    Collect

    Fetch the result by id, whole or as a replayed stream. Come back in a second or a week; the record does not expire because the connection did.

    GET /v1/requests/req_8f3a2c91
    GET …/stream?from=0

Who it’s for

Written for clients that disappear.

A phone goes into a tunnel. A field device drops to one bar. A tab is backgrounded and throttled. None of those is a failure of your code, and on most stacks all three lose the generation that was in flight.

Mobile and edge
Phones, field hardware, kiosks, browsers on hotel wifi. The client reconnects when it can and collects what it missed. Nothing in the request depends on it staying put.
Long generations
Reasoning models and agent runs that take minutes rather than seconds. Holding a socket open that long is fragile, and a serverless caller has a hard timeout it cannot argue with.
Regulated and cost-accountable
Request-level transcripts and per-key spend as a system of record — not a dashboard that rolls the numbers up and forgets the requests behind them.

Pricing

Pay for the requests you make, or take a deployment of your own.

No seats, no plan tiers, no minimum. Storage is the only thing that accrues, and you control how long you keep it.

Pay as you go

Hosted by us. Start without talking to anyone.

$0.001per request

1,000 requests cost $1. 50 MB of storage included free.

Get started
  • $0.001 per request, billed on completion
  • 50 MB of stored requests included, then $10 per GB per month
  • Retries and reconnects inside the idempotency window bill once
  • Replaying a stored stream is free, however many times
  • Bring your own provider keys — you keep your provider pricing
  • Full transcripts, per-key spend attribution, model-name routing

Enterprise

A deployment of your own. Your cloud or ours. Operated by us.

Let’s talk

Priced as an annual agreement, per deployment or by volume.

Talk to us
  • A deployment of your own, in our cloud or in your cloud account
  • We operate it either way — you do not install it or carry the pager
  • Prompts and provider keys stay in it and never enter the shared service
  • One container image and a Postgres — the whole footprint, wherever it sits
  • Self-applying migrations, so upgrades are a rolling update we run
  • Named support contact and a security review pack

Questions

What people ask before they try it.

What does it take to try it?

Two lines. Point the OpenAI or Anthropic client you already use at a Perdurance namespace URL and give it a Perdurance key instead of your provider key. The routes have your provider’s own names and take your provider’s own bodies, and the answer comes back byte for byte as the provider sent it — so no SDK is replaced, no response is unwrapped, and raising max_retries becomes safe rather than expensive.

from openai import OpenAI

client = OpenAI(
    base_url="https://api.perdurance.dev/acme/prod/v1",
    api_key=PERDURANCE_KEY,   # sar_ab12cd34_… — not your provider key
    max_retries=5,            # safe: a retry attaches, it does not re-generate
)

answer = client.chat.completions.create(
    model="gpt-4.1",
    messages=[{"role": "user", "content": "Say hello."}],
)
When is it not the right tool?

When your calls are short, your clients are stable, and re-running a failed request costs a cent — the failures it removes are ones you are not having, and this is still one more hop in your request path. It is also wrong if you want a hosted model, because it has none and you bring your own provider credential; if you need translation between provider dialects, which it deliberately does not do; if what you need made idempotent is your own tools rather than model calls; or if nobody outside your company may operate what your prompts pass through, because we operate every deployment, dedicated ones included.

Do I have to change my code?

No. Change the base URL of the OpenAI or Anthropic client you already use, and use a Perdurance API key. Requests reach the provider byte for byte and answers come back exactly as the provider sent them, with no envelope — so an unmodified vendor SDK works against it, and the retry that SDK already performs becomes the resume mechanism.

Why does a retried LLM request bill twice?

Because a retry is a second call to your provider. A client that loses its connection cannot tell whether the provider never received the request or is halfway through answering it, so it retries and pays for a second generation. Perdurance identifies a request by the bytes of its body for ten minutes, so an identical retry attaches to the execution already running and the provider is called once.

What happens if my connection drops mid-stream?

Nothing is lost. The upstream call keeps running and every chunk continues to be stored whether or not anything is reading. Reconnect and the stream replays from the first chunk, or resumes at an exact sequence number, then live-tails to completion.

Does it work with agent frameworks?

Yes. An agent stack usually retries at three layers — the vendor SDK, the framework step, and a supervisor or queue — and none of them knows the others already tried. Point the framework’s underlying provider client at Perdurance and every model call in the loop becomes idempotent, so a retry at any layer re-attaches instead of paying for a fresh generation.

Do you see my prompts, and do you train on them?

Your prompts and responses are stored so you can read them back, and they are yours. No prompt, response or stored chunk is used to train, fine-tune or evaluate any model. Provider credentials are encrypted before storage and are never returned by any route. If that is still too much, an enterprise deployment keeps your traffic out of the shared service entirely.

Can I have a deployment of my own?

Yes, as an enterprise deployment: one container image and one Postgres, dedicated to you, in our cloud or in your own cloud account. We operate it either way — you do not install it, patch it or carry the pager — and your prompts and provider keys stay in it rather than entering the shared service. It is priced as an annual agreement, per deployment or by volume.

Which providers can it route to?

OpenAI and any server that copies its API, Anthropic’s Messages API, and OpenRouter including its Anthropic-family models. You bring your own provider credential and keep your own provider pricing; Perdurance does not resell model capacity.

What does it cost?

$0.001 per request, billed on completion, with 50 MB of stored requests included and $10 per GB per month after that. There are no seats, no plan tiers and no minimum. Retries and reconnects inside the idempotency window bill once, and replaying a stored stream is free however many times you do it.

Longer answers, and the ones only a customer asks, are in the documentation FAQ.