REST API
Every resource of a network, under https:/. This reference is generated from the API’s OpenAPI 3.1 document, the contract its requests are validated against, served at /. Signed in, you can send any route to your own network from the playground.
Every route
Each route takes the network’s ID, from its settings, and one of its API keys as Authorization: Bearer cf_live_…. The paths below are under /api/v1/networks/{networkId}. Bodies are JSON unless a route takes a file. The errors and limits are the same for every route. The inbox and pitch run routes answer 404 while guest pitches are switched off.
Each route’s cost says what a call does before you send it:
- Reads The call changes nothing.
- Changes It edits or adds to what the network has.
- Deletes It removes something for good.
- Spends a model run It counts as one of the network’s daily model runs, whose turns call Qloo too.
- Calls Qloo It counts in the network’s daily Qloo calls: an import’s lookups, a comp search, measuring the roster’s overlap, profiling its listeners, or a run resumed by an answer.
- Session only Only a member’s session, from one of Crossfeed’s pages, can send it. An API key answers 403.
Two routes do more with replace=true. Importing a roster over one that has shows also changes the figures the file brings. Loading the inbox over one that has pitches also deletes them, with the last pitch run’s lists and replies, and ends a pitch run waiting on a question. The OpenAPI document gives each route’s cost as x-crossfeed-cost, and a session-only route x-crossfeed-session-only: true with the session alone as its security.
| Method | Path | What it does | Cost |
|---|---|---|---|
GET | / | Read the network | Reads |
PATCH | / | Rename the network or set its CPM | Changes |
GET | / | Read today's usage | Reads |
GET | / | Read the roster | Reads |
POST | / | Import a roster | Calls Qloo |
PATCH | / | Settle or edit a show | Changes |
POST | / | Search for a comp | Calls Qloo |
GET | / | Read the roster's overlap | Reads |
POST | / | Measure the roster's overlap | Calls Qloo |
GET | / | Read the roster's listener profile | Reads |
POST | / | Profile the roster's listeners | Calls Qloo |
GET | / | Read the inbox | Reads |
POST | / | Load the inbox | Spends a model run |
PATCH | / | Confirm a pitch's work | Changes |
GET | / | List pitch runs | Reads |
POST | / | Start a pitch run | Spends a model run |
GET | / | Read a pitch run | Reads |
POST | / | Answer a pitch run's question | Calls Qloo |
PATCH | / | Edit a reply | Changes |
POST | / | Discard a reply | Changes |
GET | / | List launches | Reads |
POST | / | Create a launch | Changes |
GET | / | Read a launch | Reads |
DELETE | / | Delete a launch | DeletesSession only |
GET | / | Read a launch's evidence | Reads |
POST | / | Start a run | Spends a model run |
GET | / | Read a run | Reads |
POST | / | Answer a run's question | Calls Qloo |
PATCH | / | Edit a draft insertion order | Changes |
GET | / | Export an approved insertion order | Reads |
Network
Read the network
GET / Reads
| Answers 200 | The network. (Network) |
|---|---|
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Rename the network or set its CPM
PATCH / Changes
A field left out stays as it is. A member's session must be an owner's; an API key, which an owner made, may.
| Body | application/json (NetworkChange) |
|---|---|
| Answers 200 | The network as changed. (Network) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 429 limit or rate_limited |
Read today's usage
GET / Reads
The network's Qloo calls and model runs today against its own daily caps, whichever member or key made them. Crossfeed's caps across all networks apply too.
| Answers 200 | Today's usage. (Usage) |
|---|---|
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Roster
Read the roster
GET / Reads
| Answers 200 | The roster. (Roster) |
|---|---|
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Import a roster
POST / Calls Qloo
Send the roster file as the body: a CSV with a name column and optional downloads, status, and description columns, or plain text with one show name per line, at most 50 shows and 5 MB. It answers 202 at once with the new shows pending; poll the roster until it settles. Over a roster that has shows, it needs replace=true: shows already on it keep their matches, comps, and exclusions, the figures the file brings change, and only new shows are looked up.
replace | In the query, optional. Import over a roster that has shows. |
|---|---|
| Body | text/csv, or text/plain |
| Answers 202 | The roster, with the import's shows pending. (Roster) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 413 too_large, 422 unreadable, 429 limit or rate_limited |
Settle or edit a show
PATCH / Changes
Pick one of an ambiguous show's candidates (entityId), map a show to one of its comp search's results (compId), or change its figures or exclusion. A field left out stays as it is.
name | The show's name as on the roster, URL-encoded. |
|---|---|
| Body | application/json (ShowChange) |
| Answers 200 | The show as changed. (Show) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 429 limit or rate_limited |
Search for a comp
POST / Calls Qloo
Search Qloo for a comparable show to stand in for one it has no match for. It answers 202 with the show's comp search pending; poll the roster until it's done, then map the show to a result with compId.
name | The show's name as on the roster, URL-encoded. |
|---|---|
| Body | application/json (CompQuery) |
| Answers 202 | The show, with its comp search pending. (Show) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Read the roster's overlap
GET / Reads
Which of the roster's shows share listeners with each other, as Qloo measured it: each show's closest shows, as ranks and bands within its own ranking, and the close pairs, two shows each among the other's closest.
| Answers 200 | The roster's overlap. (RosterOverlap) |
|---|---|
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Measure the roster's overlap
POST / Calls Qloo
Ranks the rest of the roster against each show matched in Qloo, one Qloo call each, counting shows on the same Qloo show once and including shows left out of launches. It takes at least 4 such shows and a roster with no lookup pending, and is refused while a measure runs. It answers 202 at once with the overlap measuring; poll it until it isn't. With the roster's matched shows unchanged, it asks only the shows whose ranking is missing or failed, so it's up to one call per show, and none once every ranking has landed. It counts against the network's daily Qloo calls, and is refused when the Qloo requests left today, Crossfeed's shared ones or the network's own key's, couldn't take it and still leave a run's 60.
| Answers 202 | The overlap, measuring, or as it was when there was nothing left to measure. (RosterOverlap) |
|---|---|
| Refuses | 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Read the roster's listener profile
GET / Reads
Who the roster's shows reach, as Qloo profiled them: each show's leans by age band and gender, relative to the average in Qloo, which describe listeners, not people.
| Answers 200 | The roster's listener profile. (RosterListeners) |
|---|---|
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Profile the roster's listeners
POST / Calls Qloo
Asks Qloo for the listeners of every show matched in Qloo in one call, counting shows on the same Qloo show once and including shows left out of launches. It takes at least 4 such shows and a roster with no lookup pending, and is refused while a profile is being made. It answers 202 at once with the profile profiling; poll it until it isn't. With the roster's matched shows unchanged since a profile that landed, it asks nothing. It counts against the network's daily Qloo calls, and is refused when the Qloo requests left today, Crossfeed's shared ones or the network's own key's, couldn't take it and still leave a run's 60.
| Answers 202 | The listener profile, profiling, or as it was when there was nothing to ask. (RosterListeners) |
|---|---|
| Refuses | 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Inbox
Read the inbox
GET / Reads
| Answers 200 | The inbox. (Inbox) |
|---|---|
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Load the inbox
POST / Spends a model run
Send the pitches as the body: one email as message/rfc822 (an .eml file), an mbox export as application/mbox, plain text with a line of three dashes between pitches as text/plain (a pitch's first lines may give its From: and Subject:), or JSON pitches, at most 50 pitches and 5 MB. Of each email, only its sender, subject, and text are kept, never its attachments or other headers, and only its work's title and type reach Qloo. An email with no text, or over 10,000 characters, is skipped and named. It answers 202 at once with the pitches reading; poll the inbox until it's done. Reading the pitches counts as one of the network's model runs. Over an inbox that has pitches, it needs replace=true: they go, with the last pitch run's lists and replies, and a pitch run waiting on a question ends.
replace | In the query, optional. Load over an inbox that has pitches. |
|---|---|
| Body | message/rfc822, or application/mbox, or text/plain, or application/json (PitchBatch) |
| Answers 202 | The inbox, with its new pitches reading. (Inbox) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 413 too_large, 422 unreadable, 429 limit or rate_limited |
Confirm a pitch's work
PATCH / Changes
Confirm which of an ambiguous work's same-title candidates the pitch is about (entityId). Only a work matched in Qloo is ranked.
pitchId | |
|---|---|
| Body | application/json (WorkConfirmation) |
| Answers 200 | The pitch, its work confirmed. (Pitch) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 429 limit or rate_limited |
Pitch runs
List pitch runs
GET / Reads
The network's pitch runs, newest first: the first is the latest, whose replies the inbox holds until another run or a new inbox replaces them. Read one in full by its ID.
| Answers 200 | The pitch runs. (application/json) |
|---|---|
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Start a pitch run
POST / Spends a model run
Rank the inbox's pitched works against a roster show matched in Qloo, and against its best past guests' works too, then draft a reply to every pitch. Only each work's title and type reach Qloo, never a guest's name or a sender. It answers 202 at once with the run running; poll it until it's done or waiting on a question. It counts as one of the network's model runs, and a new run ends one left waiting.
| Body | application/json (PitchRunStart) |
|---|---|
| Answers 202 | The run, running. (PitchRun) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Read a pitch run
GET / Reads
Its status, any question it waits on, and as they arrive, its ranked lists and drafted replies. An earlier run reads as it ended.
runId | The ID the run answered with when it started. |
|---|---|
| Answers 200 | The run. (PitchRun) |
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Answer a pitch run's question
POST / Calls Qloo
Answer the question the run is waiting on, by its ID: with one of its options as choice, or your own words as text. The run resumes, answering 202; poll it again. It goes on with what's left of the run's Claude turns and Qloo calls, not as a new model run. A run started later, or loading the inbox, ends a run left waiting.
runId | The ID the run answered with when it started. |
|---|---|
| Body | application/json (Answer) |
| Answers 202 | The run, resumed. (PitchRun) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Replies
Edit a reply
PATCH / Changes
Reword one of the latest pitch run's drafted replies, once the run has ended. Editing an approved reply returns it to draft, and editing a discarded one restores it. Only a member approves a reply, in the app.
runId | The ID the run answered with when it started. |
|---|---|
pitchId | |
| Body | application/json (ReplyChange) |
| Answers 200 | The reply as edited. (Reply) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Discard a reply
POST / Changes
Leave one of the latest pitch run's drafted replies out, once the run has ended. Editing it restores it.
runId | The ID the run answered with when it started. |
|---|---|
pitchId | |
| Answers 200 | The reply, discarded. (Reply) |
| Refuses | 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Launches
List launches
GET / Reads
The network's launches, newest first, as its Launches page lists them.
| Answers 200 | The launches. (application/json) |
|---|---|
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Create a launch
POST / Changes
Plan a new launch by its name, as Qloo lists a released show, or by up to three released shows as comps for an unreleased one. It joins the network's list, and every member's Launches page, with status new; start a run to rank the roster for it. A network keeps a limited number of launches at once, as the terms say: past it, a new one is refused with limit until a member deletes one on the Launches page.
| Body | application/json (LaunchPlan) |
|---|---|
| Answers 201 | The launch. (Launch) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 429 limit or rate_limited |
Read a launch
GET / Reads
Its status and figures, its runs, and its latest run in full: any question it waits on, the chart, the topic baseline, the demographics check, and the insertion order, as they arrive.
launchId | The ID the launch answered with when it was created. |
|---|---|
| Answers 200 | The launch. (Launch) |
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Delete a launch
DELETE / DeletesSession only
Delete the launch for every member, with its runs, their insertion orders, and their evidence, which can't be brought back. Only a member's session from one of Crossfeed's pages may, as the Launches page does; an API key answers 403.
launchId | The ID the launch answered with when it was created. |
|---|---|
| Answers 204 | Deleted. |
| Refuses | 401 unauthorized, 403 forbidden, 404 not_found, 429 limit or rate_limited |
Evidence
Read a launch's evidence
GET / Reads
The launch's evidence log, oldest first: one record per Qloo call its runs made, the roster's lookups each run copied as it started, and the rankings of the roster's overlap each run copied for its finalists as it drafted its order. Every call number a run cites opens one of these.
launchId | The ID the launch answered with when it was created. |
|---|---|
| Answers 200 | The evidence log. (application/json) |
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Runs
Start a run
POST / Spends a model run
Rank the network's roster, as it stands now, by fit with the launch's listeners in Qloo, then plan its promos to a draft insertion order priced at the network's CPM. With no body, the run plans the launch as it stands; a name or comps plan it anew. It answers 202 at once with the run running; poll it until it's done or waiting on a question. It counts as one of the network's model runs: past the network's daily model runs, it stops at once, saying why. A new run ends one left waiting.
launchId | The ID the launch answered with when it was created. |
|---|---|
| Body | application/json (LaunchPlan), optional |
| Answers 202 | The run, running. (LaunchRun) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Read a run
GET / Reads
Its status, any question it waits on, and as they arrive, its chart, topic baseline, demographics check, and insertion order. An earlier run reads as it ended, with its order as it was left, to compare with a re-run.
launchId | The ID the launch answered with when it was created. |
|---|---|
runId | The ID the run answered with when it started. |
| Answers 200 | The run. (LaunchRun) |
| Refuses | 401 unauthorized, 404 not_found, 429 limit or rate_limited |
Answer a run's question
POST / Calls Qloo
Answer the question the run is waiting on, by its ID, with the fields its kind takes: choice or text for a choice question; choice (one of its options) or text (the name Qloo lists the launch under) for launch; slots or dollars for budget; exclude, from its options, for exclusions; comps or text for comps; and picks for confirm_comps. Relay the question to the person planning the launch and answer with their words. The run resumes, answering 202; poll it again. It goes on with what's left of the run's Claude turns and Qloo calls, not as a new model run.
launchId | The ID the launch answered with when it was created. |
|---|---|
runId | The ID the run answered with when it started. |
| Body | application/json (Answer) |
| Answers 202 | The run, resumed. (LaunchRun) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Insertion orders
Edit a draft insertion order
PATCH / Changes
Change the lines of the launch's current order, once its run has ended: each finalist's promo slots and host-read angle, or drop a show by leaving its line out. Code prices it again at the network's CPM. Editing an approved order returns it to draft. Only a member approves an order, in the app.
launchId | The ID the launch answered with when it was created. |
|---|---|
orderId | |
| Body | application/json (OrderChange) |
| Answers 200 | The order as edited. (InsertionOrder) |
| Refuses | 400 invalid, 401 unauthorized, 403 forbidden, 404 not_found, 409 conflict, 429 limit or rate_limited |
Export an approved insertion order
GET / Reads
The order as a CSV file for ad operations: a row per line, then the total, in whole dollars. Only an order a member approved in the app exports; a draft answers 409. An earlier run's order exports as it was left.
launchId | The ID the launch answered with when it was created. |
|---|---|
orderId | |
| Answers 200 | The order as CSV. (text/csv) |
| Refuses | 401 unauthorized, 404 not_found, 409 conflict, 429 limit or rate_limited |