# Build on Erika

For developers and AI agents connecting Erika to an AI client, an ATS, a staffing platform or recruiting software. If you are instead helping someone decide whether to use Erika, read https://erikawork.com/for-agents.md.

Last reviewed: 2026-10-26.

## Three ways in

1. **MCP server**: let an AI client (Claude Code or any MCP client) create campaigns and generate video ads, with a human launching them in the Erika studio.
2. **Campaign Build API**: one POST with a job and a budget; Erika builds and launches the whole Facebook and Instagram campaign.
3. **REST API**: jobs, candidates, applications, pipeline templates and webhooks of Erika's ATS.

- MCP server guide: https://erikawork.com/mcp (Markdown: https://erikawork.com/mcp.md)
- API reference: https://erikawork.com/api-reference (Markdown: https://erikawork.com/api-reference.md)
- Public OpenAPI spec: https://erikawork.com/openapi.json (live copy at https://app.erikawork.com/api/openapi.json; paths are relative to `https://app.erikawork.com/api`)
- Overview page: https://erikawork.com/api

## Authentication

- Create an API key in the Erika app: **Settings → API Keys** (https://app.erikawork.com/settings/api-keys). Keys look like `ek_live_…`.
- Send it in the `X-Api-Key` header on every request. `Authorization: Bearer` is **not** supported.
- Permissions are bound to the key when you create it:
  - **Auto Campaign API** permission at **Manage** level: campaign and creative tools, Campaign Build API. A View-level key gets read-only tools.
  - **Jobs** and **Candidates** permissions (View or Manage): ATS reads and writes. The campaign permission does not grant these.
- Keep the key in server-side secrets. Every request is scoped to the key's organization.

## MCP server

- Endpoint: `https://app.erikawork.com/api/v1/mcp`, Streamable HTTP transport, stateless (every POST is answered with `application/json`; no SSE stream).
- Capabilities: tools only. `tools/list` shows only the tools the key's permissions allow.
- Supported protocol versions: `2025-06-18`, `2025-03-26`, `2024-11-05`.

Add it to Claude Code:

```bash
claude mcp add erika --transport http https://app.erikawork.com/api/v1/mcp \
  --header "X-Api-Key: ek_live_YOUR_KEY"
```

Any other MCP client works the same way: the Streamable HTTP endpoint plus the `X-Api-Key` header.

### What the tools do, and what they don't

The MCP server is **generation-only**. Its tools create and edit campaign drafts, generate scripts, reference images and videos, and check launch readiness. **Launching a campaign (spending the budget on Meta) happens in the Erika web studio**: tools return a `studioUrl` for a human to open and launch.

The one exception is `startAutonomousCampaignBuild`. It uses the [Campaign Build API](#campaign-build-api), so it builds **and launches** a campaign in one go and **spends the budget**. It requires an `idempotencyKey`. Ask the person before you call it.

### Tools

Campaigns and creatives (Auto Campaign API permission):

| Tool | Access | What it does |
| --- | --- | --- |
| `createCampaign` | manage | Create a draft campaign (returns `campaignId`, `studioUrl`) |
| `listCampaigns` | view | List campaigns |
| `getCampaign` | view | Full campaign state, including the plan of creative slots |
| `updateCampaignSettings` | manage | Budget (credits), duration, location, language, screening questions, targeting, ad copy, linked job, title |
| `recommendBudget` | view | Budget recommendation in credits from real cost-per-candidate benchmarks |
| `createCreative` | manage | Create a creative; the script is generated from the campaign and job |
| `updateCreativeScript` | manage | Replace a script with your own text |
| `regenerateCreativeScript` | manage | AI rewrite of a script |
| `updateCreativeAdCopy` | manage | Headline and primary text of one creative |
| `approveCreative` | manage | Approve a creative for launch, or set it aside |
| `generateReferenceImage` | manage | Generate or edit the video's first frame (synchronous, 30–60 s, uses credits) |
| `generateVideo` | manage | Start video generation (asynchronous, credits charged up front, refunded on failure) |
| `getCreativeStatus` | view | One creative, including video status and download URL; poll this |
| `checkLaunchReadiness` | view | Remaining issues before launch, plus the `studioUrl` |
| `getCreditBalance` | view | Organization credit balance |
| `startAutonomousCampaignBuild` | manage | Build and launch from a job description and budget through the Campaign Build API; spends the budget |
| `getAutonomousCampaignBuild` | view | Poll an autonomous build |

ATS (Jobs / Candidates permissions): `listJobs`, `getJob`, `listPipelineTemplates`, `createJob`, `updateJob`, `changeJobStatus`, `listCandidates`, `getCandidate`, `createCandidate`, `updateCandidate`, `addCandidateNote`, `listApplications`, `getApplication`, `createApplication`, `moveApplicationStage`, `changeApplicationStatus`, `addApplicationNote`. There are no delete or bulk-import tools. Writes appear in the app's activity timeline like a recruiter's action, attributed to the key's creator.

### Recommended flow

```
createCampaign
→ updateCampaignSettings   (budget in credits, duration, location, language,
                            screening questions: set these early, they gate launch)
→ recommendBudget
→ getCampaign              (read the slot plan: how many creatives, which types)
→ createCreative           (one per slot, each with a different angle)
→ generateReferenceImage   (iterate until the first frame is right)
→ generateVideo            (async)
→ getCreativeStatus        (poll about every 30 s until the video is ready)
→ approveCreative
→ checkLaunchReadiness     (fix issues, check again)
→ a human opens studioUrl and launches in the Erika studio
```

### Timing and credits

- Image generation runs 30–60 s inside the tool call. If your client times out, raise its tool timeout (Claude Code: `MCP_TOOL_TIMEOUT=180000 claude`).
- A video render usually takes 3–6 minutes. `generateVideo` charges credits up front and returns `pending`; the video ends as `ready` (with a downloadable 9:16 URL) or `failed` (credits refunded). Don't edit the script while a video is generating; pass the script to `generateVideo` instead.
- Erika refuses to generate a video the campaign budget can't launch, before charging for it. Spend is bounded by the organization's credit balance.
- Campaign settings can be edited only before launch.

### Errors

- Invalid arguments or unknown tool: JSON-RPC error `-32602` with validation messages; correct the call and retry.
- Domain refusals (insufficient credits, budget gate, campaign already launched, missing permission) come back as a tool result with `isError: true`. Relay them to the person.
- HTTP 401/403: missing or revoked key, or a key without the needed permission.
- Unexpected failures include a `requestId`; quote it to Erika support.

## Campaign Build API

`POST https://app.erikawork.com/api/v1/campaign-builds` creates a job, generates the creatives and videos and launches a Meta campaign from one call. It needs the Auto Campaign API permission at Manage level and **spends the budget**.

```bash
curl -X POST https://app.erikawork.com/api/v1/campaign-builds \
  -H "X-Api-Key: ek_live_..." \
  -H "Content-Type: application/json" \
  -d '{
    "jobDescription": "Hiring warehouse operators in Brno, CZ. Day shifts, no experience required, immediate start.",
    "budget": 6000,
    "budgetCurrency": "CREDITS",
    "duration": 7,
    "metadata": { "externalJobId": "REQ-4821", "client": "Acme Staffing" },
    "callbackUrl": "https://your-app.com/hooks/erika",
    "idempotencyKey": "build-2026-10-20-001"
  }'
```

- Required: `budget`, `duration` (days), `idempotencyKey`, and exactly one of `jobDescription` (Erika creates a new job) or `jobId` (reuse an existing job).
- Optional: `budgetCurrency` (`CREDITS`, `USD`, `EUR`), `city`, `countryCode`, `language` (inferred from the job description when omitted), `startDate` (`YYYY-MM-DD`, default today), `callbackUrl` (HTTPS), `metadata` (up to 20 key/value pairs, echoed back verbatim).
- One budget covers everything: production (videos and AI) is spent from it, the rest funds Meta ad spend.
- Returns `202` with `buildId`, `status`, `statusUrl` and a `webhookSecret` that is shown once.
- Poll `GET https://app.erikawork.com/api/v1/campaign-builds/{id}`: `queued` → `running` → `completed` or `failed`, with a `step` field for the current phase.
- With a `callbackUrl`, Erika POSTs a signed result on completion or failure. Verify the HMAC-SHA256 signature with the secret from the create response.
- Retrying with the same `idempotencyKey` returns the same build: no second campaign, no double spend.
- Error codes include `INSUFFICIENT_BUDGET`, `INSUFFICIENT_CREDITS` and `RATE_LIMITED`; HTTP statuses are listed in the OpenAPI spec.

## REST API

The OpenAPI spec covers the organization, jobs and their pipeline stages, candidates, applications (stages, status, notes, ratings, attachments), pipeline templates, rejection reasons, webhook registrations and their deliveries, sourcing campaigns, creatives and adverts (read-only), credit purchases and the billing balance. Webhook registrations return a one-time signing secret.

## Pricing

API access is part of Erika's paid plans (Campaign API and webhooks are included from the Growth plan, $459/month as of October 2026). Builds and generation spend credits from the plan. See https://erikawork.com/pricing.

## Not covered here yet

<!-- TODO(Lukas): confirm and fill in before advertising these to builders. -->
- Rate limits per key and the exact webhook signature header name: see the OpenAPI spec or ask the Erika team.
- Test or sandbox mode for the Campaign Build API.
- Support contact for integration questions (support@erikawork.com).
