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

# Async jobs

> The create-then-poll pattern shared by exports, reindexes, deletions, and schema rebuilds.

Long-running operations in Splendor are asynchronous. They follow one pattern: a request creates a job and returns it immediately with a status; you then poll the job until it finishes. Nothing blocks while the work runs.

## The pattern

1. **Create** — the operation returns a job object with an identifier and an initial status (for example `pending` or `running`).
2. **Poll** — fetch the job by its identifier until its status is terminal (`succeeded`/`completed`, `failed`, or `cancelled`).
3. **Act** — read the job's result (a download URL, updated readiness, a count).

## Jobs by operation

| Operation       | Create                                                | Poll                                                           |
| --------------- | ----------------------------------------------------- | -------------------------------------------------------------- |
| Export          | `POST /v1/export`                                     | `GET /v1/export/{export_id}`                                   |
| Reindex         | `POST /v1/admin/reindex/jobs`                         | `GET /v1/admin/reindex/jobs/{job_id}`                          |
| Data deletion   | `DELETE /v1/admin/datasets/{dataset_id}`              | `GET /v1/admin/data-deletion-jobs/{job_id}`                    |
| Schema rebuild  | `POST /v1/admin/datasets/{dataset_id}/schema/rebuild` | `GET /v1/admin/datasets/{dataset_id}/schema/rebuilds/{job_id}` |
| Filter backfill | `POST /v1/admin/semantic/filters/backfill`            | `GET /v1/admin/semantic/filters/backfill/{job_id}`             |
| Ingestion       | upload or stream                                      | `GET /v1/ingest/runs/{ingest_run_id}`                          |

<Note>
  Declare a new [filterable field](/concepts/search-model#filtering-on-metadata) and existing records won't carry it until they are re-read. A **filter backfill** applies the new field to already-indexed records without re-embedding them — it re-extracts each record's filter values and restamps them onto the existing vectors. Scope it to a `dataset_id` (and optionally one `source_id`); the job reports the sources and objects it processed.
</Note>

## Polling

Poll on an interval with backoff; there is no need to poll more than every few seconds. Reindex and deletion jobs report per-item progress counts you can surface to users.

```python theme={null}
import time

def wait_for_export(client, export_id, interval=3):
    while True:
        job = client.get(f"/v1/export/{export_id}").json()
        if job["status"] in {"completed", "failed"}:
            return job
        time.sleep(interval)
```

<Note>
  Reindex jobs can be cancelled while in flight with `POST /v1/admin/reindex/jobs/{job_id}/cancel`. Data-deletion jobs run through the managed deletion worker and cannot be cancelled once started.
</Note>
