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

# Idempotent requests

> Retry safely after a network failure without generating and being charged twice.

Every request that starts generation accepts an `Idempotency-Key` header: a
value you choose, 1 to 255 characters, that ties retries of the same request
to one job.

Send it on campaigns, photoshoots, moodboards, ChatGPT ad groups and ads,
listing images and videos. It is optional, but it is what makes a retry after
a dropped connection safe: with the same key and the same body, LocalAds
returns the original job instead of starting and charging for a second one.

## Rules

* One key per logical request. A new request, even an identical body submitted
  deliberately again, gets a new key.
* The key is matched against the request body. The same key with a different
  body returns `409 idempotency_conflict`.
* While the first request with a key is still running, a retry with the same
  key and body returns `409 idempotency_in_progress`. Wait and retry shortly;
  you get the original job when it finishes.
* A key can be any unique string: a UUID, or a stable value you derive per
  request such as `quick-shoot-1042`.

## After an ambiguous failure

A network timeout or a dropped connection leaves you not knowing whether the
job started. This is exactly the case the key exists for:

1. Send an `Idempotency-Key` on every request that spends credits, before you
   need it.
2. On an ambiguous failure, retry the identical request with the identical
   key.
3. Interpret the response:
   * the original job's resource, if it was accepted;
   * `409 idempotency_in_progress`, if it is still running: retry shortly;
   * the job freshly accepted, if the first attempt never arrived.

Your balance is charged once either way.

## Where it is accepted

| Request | Header |
| - | - |
| `POST /campaigns`, `POST /campaigns/{campaign_id}/creatives` | `Idempotency-Key` |
| `POST /photoshoots` | `Idempotency-Key` |
| `POST /moodboards`, `POST /templates` | `Idempotency-Key` |
| `POST /chatgpt-ad-groups`, `POST /chatgpt-ad-groups/{ad_group_id}/ads` | `Idempotency-Key` |
| `POST /amazon-listing-images`, `POST /amazon-listing-ideas/{idea_id}/image` | `Idempotency-Key` |
| `POST /videos` | `Idempotency-Key` |
| `POST /brands`, `POST /products` | `Idempotency-Key` |

See [Errors and retries](/concepts/errors) for the two `409` codes.
