# POST /v1/projects/:projectId/content/ugc-remix (/docs/api/reference/content/ugc-remix)



<Endpoint method="POST" path="/v1/projects/:projectId/content/ugc-remix" scope="content:write" phase="1">
  Starts a content-generate [job](/docs/api/concepts/jobs). Returns `202`
  with `containerIds` (single-element array — the partner surface never
  fans out variants) and `jobId`.
</Endpoint>

UGC remix is the only format with no required creative input — the workflow auto-selects a reaction template, music track, and app-demo source unless the partner pins specific values. The influencer is the on-camera actor; one of `socialAccountId` (with a wired influencer) or `influencerId` is required.

## Path parameters [#path-parameters]

<Parameters
  rows="[
  { name: 'projectId', type: 'string (uuid)', required: true, description: 'The project to generate content for.' },
]"
/>

## Body [#body]

<Parameters
  title="Body"
  rows="[
  { name: 'socialAccountId', type: 'string', description: 'Connected social-account id. Walks the wiring chain to find the influencer voice/language and the layer the container is anchored to.' },
  { name: 'influencerId', type: 'string', description: 'Explicit influencer override. Wins over the wired influencer. One of socialAccountId or influencerId is required.' },
  { name: 'hook', type: 'string', description: 'Optional opening overlay text. 1–2000 chars; line breaks and emoji preserved. Defaults to no overlay.' },
  { name: 'mediaId', type: 'string', description: 'Partner-uploaded app-demo source clip. Defaults to the project\'s first `media_role: &#x22;app-demo&#x22;` row.' },
]"
/>

## Defaults when fields are omitted [#defaults-when-fields-are-omitted]

* **Reaction template** — random pull from our public reaction-video pool.
* **Music** — random trending track.
* **App-demo source** — the project's first `media_role: "app-demo"` row in `media_library`, unless the partner pinned one via `mediaId`.

## Request [#request]

<Tabs items="['curl', 'TypeScript', 'Python']">
  <Tab value="curl">
    ```sh title="terminal"
    curl -X POST https://api.layers.com/v1/projects/{projectId}/content/ugc-remix \
      -H "Authorization: Bearer $LAYERS_API_KEY" \
      -H "Content-Type: application/json" \
      -H "Idempotency-Key: $(uuidgen)" \
      -d '{
        "influencerId": "inf_4a8e1bc2..."
      }'
    ```
  </Tab>

  <Tab value="TypeScript">
    ```ts title="ugc-remix.ts"
    const res = await fetch(
      `https://api.layers.com/v1/projects/${projectId}/content/ugc-remix`,
      {
        method: 'POST',
        headers: {
          'Authorization': `Bearer ${process.env.LAYERS_API_KEY}`,
          'Content-Type': 'application/json',
          'Idempotency-Key': crypto.randomUUID(),
        },
        body: JSON.stringify({ socialAccountId: 'sac_...' }),
      },
    );
    const { jobId, containerIds } = await res.json();
    const [containerId] = containerIds;
    ```
  </Tab>

  <Tab value="Python">
    ```py title="ugc_remix.py"
    import os, uuid, httpx

    r = httpx.post(
        f"https://api.layers.com/v1/projects/{project_id}/content/ugc-remix",
        headers={
            "Authorization": f"Bearer {os.environ['LAYERS_API_KEY']}",
            "Idempotency-Key": str(uuid.uuid4()),
        },
        json={"influencerId": "inf_4a8e1bc2..."},
    )
    job = r.json()
    ```
  </Tab>
</Tabs>

## Responses [#responses]

<Response status="202" description="Job accepted.">
  ```json
  {
    "jobId": "job_01HZX3...",
    "kind": "content_generate",
    "status": "running",
    "containerIds": ["cnt_7d18b9a1..."],
    "locationUrl": "/v1/jobs/job_01HZX3..."
  }
  ```
</Response>

<Response status="422" description="Influencer required, app-demo missing, or wiring resolution failed.">
  ```json
  {
    "error": {
      "code": "VALIDATION",
      "message": "MISSING_APP_DEMO: ugc-remix requires an app-demo asset on the project. Upload one via POST /v1/projects/:id/app-media with kind='demo-video' before retrying.",
      "requestId": "req_...",
      "details": {
        "code": "MISSING_APP_DEMO",
        "format": "ugc-remix"
      }
    }
  }
  ```

  The top-level `error.code` is the generic `VALIDATION` envelope. The specific failure code lives at `error.details.code` — that's what partners switch on programmatically.

  | `details.code`                                                          | Cause                                                                          |
  | ----------------------------------------------------------------------- | ------------------------------------------------------------------------------ |
  | `INFLUENCER_REQUIRED`                                                   | Neither `socialAccountId` (with wired influencer) nor `influencerId` provided. |
  | `MISSING_APP_DEMO`                                                      | `mediaId` not supplied AND project has no `media_role: "app-demo"` row.        |
  | `ACCOUNT_NOT_WIRED` / `NO_CONTENT_LAYER_WIRED` / `INFLUENCER_NOT_WIRED` | Wiring chain resolution failed mid-step.                                       |
</Response>

<Response status="404" description="`socialAccountId`, `influencerId`, or `mediaId` not on this project.">
  ```json
  { "error": { "code": "NOT_FOUND", "message": "mediaId is not on this project.", "requestId": "req_..." } }
  ```
</Response>

## Errors [#errors]

| Code                   | When                                                                 |
| ---------------------- | -------------------------------------------------------------------- |
| `VALIDATION`           | Body shape invalid.                                                  |
| `NOT_FOUND`            | `socialAccountId`, `influencerId`, or `mediaId` not on this project. |
| `INFLUENCER_REQUIRED`  | No influencer resolvable from either path.                           |
| `MISSING_APP_DEMO`     | No `mediaId` AND no app-demo on the project.                         |
| `IDEMPOTENCY_CONFLICT` | Same `Idempotency-Key` reused with different body.                   |
| `BILLING_EXHAUSTED`    | Org wallet at zero.                                                  |

## See also [#see-also]

* [Upload app media — upload an app-demo via public URL](/docs/api/reference/app-media/upload-app-media)
* [The jobs envelope](/docs/api/concepts/jobs)
* [Approve generated content](/docs/api/reference/approval/approve-content)
