# Quickstart

> Run your first job: find a task, check its cost, submit it, get the files.

## 1. Get a key

Create a key in **Panel › Developers › Keys**. The key is shown **once** — store it in a secret
manager or an environment variable.

```bash
export REFABRIC_API_KEY="<key>"
export REFABRIC_API="https://api.refabric.com/v1"
```

## 2. Find a task

```bash
curl -s "$REFABRIC_API/tasks" -H "Authorization: Key $REFABRIC_API_KEY"
```

Each entry has a `name`, a `title`, a `summary`, a `category`, and — on `GET /v1/tasks/{name}` —
the full `inputSchema` and `outputSchema`, every field explained.

`category` says what kind of work the task does: `generation` makes new content (its inputs, including a
file from an earlier result, guide it — `image.generate`, `moodboard.create`); `edit` makes another
version of the one image or record you give it (`image.<verb>`, e.g. `image.change_background`; and
`fabric.add_colour`, a new colour of your fabric) ([Files](https://docs.refabric.com/task-apis/files-and-media)).

```bash
curl -s "$REFABRIC_API/tasks/image.glam" -H "Authorization: Key $REFABRIC_API_KEY"
```

> `image.glam` changes one feature of a finished image; the published list of tasks is what
> `GET /v1/tasks` returns.

## 3. Check the cost

```bash
curl -s -X POST "$REFABRIC_API/tasks/image.glam/estimate" \
  -H "Authorization: Key $REFABRIC_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"prompt": "make the lipstick red", "image": "https://example.com/look.png"}'
```

```json
{ "task": "image.glam", "ceiling": <credits>, "credit_type": "<credit type>", "is_ceiling": true }
```

`credit_type` is one of the values at `GET /v1/vocab/credit_type`.

## 4. Submit

```bash
curl -s -X POST "$REFABRIC_API/tasks/image.glam" \
  -H "Authorization: Key $REFABRIC_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: $(uuidgen)" \
  -d '{"prompt": "make the lipstick red", "image": "https://example.com/look.png"}'
```

```json
HTTP/1.1 202 Accepted
X-Request-ID: req_…
X-Refabric-Credits: <credits held>
X-Refabric-Credit-Type: <credit type>

{
  "job_id": "j_…",
  "lifecycle": "queued",
  "status_url": "https://api.refabric.com/v1/jobs/j_…",
  "result_url": "https://api.refabric.com/v1/jobs/j_…/result",
  "cancel_url": "https://api.refabric.com/v1/jobs/j_…/cancel"
}
```

## 5. Get the result

Poll the status until it is terminal, then read the result:

```bash
curl -s "$REFABRIC_API/jobs/j_…" -H "Authorization: Key $REFABRIC_API_KEY"
curl -s "$REFABRIC_API/jobs/j_…/result" -H "Authorization: Key $REFABRIC_API_KEY"
```

```json
{
  "job_id": "j_…",
  "files": [
    { "file": "art:x1", "url": "https://…", "media_type": "image/png",
      "task": "image.glam", "job_id": "j_…", "created_at": "2026-09-28T10:00:00Z" }
  ],
  "has_more": false
}
```

Short jobs can skip polling with `Prefer: wait=N` (see [Jobs](https://docs.refabric.com/task-apis/calling-tasks/synchronous)); long ones
should use a [webhook](https://docs.refabric.com/task-apis/calling-tasks/webhooks).

## The same in Python

```python
import os, time, uuid
import requests

API = os.environ.get("REFABRIC_API", "https://api.refabric.com/v1")
s = requests.Session()
s.headers["Authorization"] = f"Key {os.environ['REFABRIC_API_KEY']}"

body = {"prompt": "make the lipstick red", "image": "https://example.com/look.png"}

job = s.post(f"{API}/tasks/image.glam", json=body,
             headers={"Idempotency-Key": str(uuid.uuid4()), "Prefer": "wait=30"})
job.raise_for_status()

if job.status_code == 200:            # finished within the wait
    result = job.json()
else:                                 # 202: still running — poll
    handle = job.json()
    while True:
        status = s.get(handle["status_url"]).json()
        if status["lifecycle"] == "terminal":
            break
        time.sleep(5)
    if status["outcome"] != "succeeded":
        raise RuntimeError(status.get("error"))
    result = s.get(handle["result_url"]).json()

for f in result["files"]:
    print(f["file"], f["media_type"], f["url"])
```

## Continue from a result

Pass a file back as the input of the next job — no ids needed:

```json
{ "prompt": "now add a white collar", "image": "art:x1" }
```

Next: [Authentication](https://docs.refabric.com/api-reference/platform/authentication) · [Jobs](https://docs.refabric.com/task-apis/calling-tasks/asynchronous-jobs) · [Files](https://docs.refabric.com/task-apis/files-and-media).
