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

# Requesting a Creator

> Ask the Streamforge API to prepare a creator profile and audience analysis that are not available yet, then poll the request until it finishes.

The profile and audience endpoints answer from data Streamforge already holds. When they answer `404` for a creator you need, or a creator has a profile but no audience analysis, ask for the creator with a **creator request** and check back for the result.

> [!NOTE]
>
> Creator requests are available with a Streamforge API key only, not through RapidAPI.

## How it works

1. `POST /creator-requests` with the creator you want.
2. If everything you asked for can already be served, the answer is `200` and the data is in `result`. You are done.
3. Otherwise the answer is `202` with a `request_id`. Read `GET /creator-requests/{request_id}` every few seconds until it answers `200`.

Both endpoints return the same body, so one piece of code can handle either.

## Step 1: Make the request

Name the creator by platform and handle, by platform and profile ID, or with a profile URL:

```bash theme={null}
curl -i -X POST https://external-api.streamforge.com/creator-requests \
  -H "x-api-key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"platform": "youtube", "handle": "@examplecreator"}'
```

Any one of these bodies names a creator:

```json theme={null}
{ "platform": "youtube", "handle": "@examplecreator" }
{ "platform": "youtube", "profile_id": "UCxxxxxxxxxxxxxxxxxxxxxx" }
{ "url": "https://www.youtube.com/@examplecreator" }
```

Add `"audience": false` if you only need the profile.

A URL has to be a creator's profile or channel. A link to a video, a post or a search page is rejected with `400` and the code `unsupported_profile_url`.

When there is work to do, the answer is `202`:

```
HTTP/1.1 202 Accepted
Location: /creator-requests/cr_3f9a1c2b4d5e6f708192a3b4c5d6e7f8
Retry-After: 3
```

```json theme={null}
{
  "payload": {
    "request_id": "cr_3f9a1c2b4d5e6f708192a3b4c5d6e7f8",
    "status": "pending",
    "stage": "queued",
    "progress": 0,
    "message": "Queued",
    "platform": "youtube",
    "handle": "examplecreator",
    "profile_id": null,
    "parts": { "profile": "pending", "audience": "pending" },
    "audience_reason": null,
    "poll_after_seconds": 3,
    "status_url": "/creator-requests/cr_3f9a1c2b4d5e6f708192a3b4c5d6e7f8",
    "result": null
  },
  "meta": {
    "received_at": "2026-10-13T12:00:00.000Z",
    "credits_charged": 1
  }
}
```

## Step 2: Poll until it finishes

Read the request at `status_url`, waiting `poll_after_seconds` between reads. The answer stays `202` while the request is `pending` or `processing` and becomes `200` when it has finished:

```bash theme={null}
REQUEST_ID=cr_3f9a1c2b4d5e6f708192a3b4c5d6e7f8

while true; do
  STATUS=$(curl -s -o response.json -w "%{http_code}" \
    -H "x-api-key: YOUR_API_KEY" \
    "https://external-api.streamforge.com/creator-requests/$REQUEST_ID")

  if [ "$STATUS" != "202" ]; then break; fi
  sleep 3
done

cat response.json
```

`result.profile` is filled in as soon as the profile can be served, which can be while the audience analysis is still in progress. `stage`, `progress` and `message` are there for showing progress to a person; decide what to do next from `status` and `parts`.

## Step 3: Read the outcome

A finished request has one of four statuses:

| Status | What you have |
| - | - |
| `ready` | The profile in `result.profile`, and the audience analysis in `result.audience` if you asked for it |
| `partial` | The profile in `result.profile`, and no audience analysis. `parts.audience` and `audience_reason` say why |
| `not_found` | Nothing: there is no such creator on that platform |
| `failed` | Nothing: the request could not be completed. You can make it again |

`result.profile` is the same object [Get single profile](https://docs.streamforge.com/api-reference/profiles/get-profile.md) returns, and `result.audience` the same object [Get audience analysis](https://docs.streamforge.com/api-reference/advanced/get-audience-analysis.md) returns. `profile_id` is the ID to use with every other endpoint from then on.

### When the audience analysis is not available

`partial` is an ordinary outcome, not an error. An audience analysis is not always possible, and `parts.audience` tells you which case you are in:

| `parts.audience` | Meaning |
| - | - |
| `insufficient_data` | There is not enough public audience data for this creator to produce an analysis |
| `unsupported` | An audience analysis is not available for this creator on this platform |
| `unavailable` | The daily capacity for new analyses is used up. Request the creator again after the daily reset |
| `failed` | The analysis could not be completed |

`audience_reason` carries the same explanation as a sentence you can show.

## Credits

| Call | Credit Cost |
| - | - |
| `POST /creator-requests`, accepted (`200` or `202`) | 1 credit, once |
| `POST /creator-requests` again for the same request while it is in progress | 0 credits; you get the same `request_id` |
| `GET /creator-requests/{request_id}` | 0 credits |
| A request that ends `not_found` or `failed` | The credit is returned |

`meta.credits_charged` shows what the request has cost in total, and the `X-Credits-request-cost` response header what the call you just made cost. Both are in credits. Reads are free but do count towards your per-minute rate limit, so keep to `poll_after_seconds`.

## Errors

| Status | Code | What to do |
| - | - | - |
| `400` | `unsupported_profile_url`, `platform_mismatch`, `invalid_handle`, `invalid_profile_id` | Fix the request; it does not name a creator profile |
| `403` | `direct_key_only` | Use a Streamforge API key; these endpoints are not on RapidAPI |
| `404` | `creator_request_not_found` | The `request_id` is wrong, has expired, or belongs to another API key |
| `503` | `preparation_unavailable` | Nothing was started or charged. Try again after `Retry-After` seconds |
| `503` | `preparation_budget_exhausted` | The daily capacity for preparing new creators is used up. Nothing was charged; try again after the daily reset |

A request can be read only with the API key that created it, and stays readable for 7 days.

## Best practices

* **Use the profile endpoint when a profile is all you need** and you have its ID: it costs 0.01 credit for a creator that is already available, where a creator request costs 1 credit.
* **Keep the `request_id`** rather than posting again: a new `POST` after the request has finished starts, and charges, a new request.
* **Treat `partial` as a result**: the profile is usable even when no audience analysis could be produced.
* **Respect `Retry-After`** on `202`, `429` and `503` answers.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.