# Idempotency



> Import and export job creation endpoints accept idempotency keys so network retries do not queue duplicate work. This guide explains when to use a key, how to choose one, and how to store the key with your own job record.



- Human page: https://mailrith.com/developers/idempotency

- Markdown page: https://mailrith.com/developers/idempotency.md

- Category: API Concepts

- Reading time: 5 min read

- Last updated: 2026-07-13

- Related keywords: Idempotency, Idempotency developer docs, API Concepts, API Concepts developer docs, Mailrith developer docs, Mailrith public API, Use Idempotency for Async Job Creation, Keep Retries Safe, Import and Export Jobs, Errors, Testing the API



## AI Agent Notes

- Use this page as implementation guidance, then validate exact endpoint fields against the OpenAPI document.

- Keep API keys server-side and workspace-scoped unless a guide explicitly says otherwise.

- Do not invent privacy, consent, or lawful-basis evidence. Send only fields that appear in the OpenAPI schema for the endpoint you are using.



## What this guide covers

Retry import and export job creation safely with the `Idempotency-Key` header.



## Use Idempotency for Async Job Creation

Idempotency protects create-style requests from accidental duplication. In Mailrith's public API, idempotency is most important when queueing subscriber import and export jobs because those jobs can continue doing significant work after the request returns.

If your integration sends a job creation request and the network times out, your integration may not know whether Mailrith received the request. Repeating the request with the same `Idempotency-Key` lets Mailrith return the original job response instead of creating another job.

Use idempotency keys for import and export job creation whenever the caller, queue worker, or HTTP client might retry a request automatically.

1. Create your own local job record before sending the Mailrith request.
2. Generate one idempotency key for that local job.
3. Send the Mailrith import or export request with `Idempotency-Key` and the job payload.
4. If the request succeeds, store the returned Mailrith job ID.
5. If the request times out, retry with the same key and the exact same payload.
6. If the CSV, mappings, or export filters change, create a new local job and a new idempotency key before sending another request.
7. Monitor the job as described in [Import and Export Jobs](https://mailrith.com/developers/jobs.md).

- Generate one idempotency key for one logical job submission.
- Reuse the same key only for retries of the exact same request body.
- Store the key with your own job record so a queue worker can retry safely after a crash.
- Use a new key when the CSV content, mappings, filters, or export selection changes.
- Do not use one long-lived key for every import or export. A long-lived key would make different jobs look like the same request.

Related OpenAPI operation groups:
- Jobs

## Keep Retries Safe

A safe retry pattern starts before the HTTP request is sent. First create your own local job record, then generate an idempotency key, then send the Mailrith request with that key.

If the request succeeds, store Mailrith's returned job ID beside your own job record. If the request times out, retry with the same key and the same request body. If Mailrith already created the job, Mailrith can return the original response.

If you change the payload after a failed attempt, create a new idempotency key before retrying. A changed payload is no longer the same logical job.

- Good key examples: `import_2026_04_25_crm_001`, a UUID, or your own queue job ID.
- Bad key examples: `import`, `retry`, the workspace ID, or the API key.
- Keep idempotency keys out of user-visible copy. They are operational identifiers, not labels.
- Log the idempotency key with your job ID so you can trace repeated attempts.

**Import Job With an Idempotency Key**

```bash
curl -X POST https://api.mailrith.com/v1/jobs/subscriber-imports \
  -H "Authorization: Bearer mrk_example_secret_key" \
  -H "Idempotency-Key: import-2026-04-11-website-signups" \
  -H "Content-Type: application/json" \
  -d '{
    "csv_text": "Email,Name,Country,Subscriber Status\nada@example.com,Ada Lovelace,DE,Active",
    "mappings": [
      {
        "csv_column": "Email",
        "field": { "type": "email" }
      },
      {
        "csv_column": "Name",
        "field": { "type": "name" }
      },
      {
        "csv_column": "Country",
        "field": { "type": "country" }
      },
      {
        "csv_column": "Subscriber Status",
        "field": { "type": "subscriber-status" }
      }
    ],
    "new_tag_name": "Website Signup"
  }'
```



## Related Guides

- [Import and Export Jobs](https://mailrith.com/developers/jobs.md): Imports and exports are asynchronous in `v1`. This guide explains when to queue a job, how import mappings and export filters work at a high level, how to use idempotency, and how to monitor final job status without confusing queued work with completed work.

- [Errors](https://mailrith.com/developers/errors.md): Non-2xx responses include stable error codes and plain-language messages. This guide explains how to log errors, avoid matching on message text, map status codes to user or system actions, and retry only when the same request may succeed later.

- [Testing the API](https://mailrith.com/developers/testing-the-api.md): You can test Mailrith's public API manually with local curl requests or automatically with the integration suite. This page shows the repo-native commands for both testing paths.
