A Wave campaign is paid media run against one event. Wave’s wizard configures campaigns and pushes them to ad platforms; the same wizard edits them after publish.

The atom: setup_process

There is one setup_process per event, stored under /setup_processes/{eid}. It holds:
  • Goal (UTILIZATION, ROAS, VISIBILITY, LINK_CLICKS).
  • Total budget, start date, end date.
  • Selected taste clusters at a fixed tc_run_id.
  • Creatives per cluster (headline, body, media, CTA).
  • Targeting per cluster (geo, demographics, custom audiences).
  • Integration details (ad account, pixel, lead form, …).
  • DSA payor / beneficiary (EU compliance).
Lifecycle endpoints:
POST   /setup_processes/{eid}        # start draft
PUT    /setup_processes/{eid}        # autosave every ~1s of edits
GET    /setup_processes/{eid}        # read back; 404 if no draft
DELETE /setup_processes/{eid}        # cancel draft
POST   /setup_processes/{eid}/boost  # publish → creates campaigns
POST   /campaigns_setup              # edit one published cluster
See Wave Campaigns Lifecycle for the full state machine and call chains.

Reading published campaigns

After publish, list campaigns under an event:
GET /events/{eid}/campaigns
Each campaign carries its composite identifier (eid, tc, tc_run_id).

Post-campaign performance

Campaign performance is read via the Meta integration endpoint:
GET /integrations/facebook/events/{eid}/campaign_results
GET /integrations/facebook/events/{eid}/fb_insights
Partner scope comes from the X-Preferred-Partner-Id header. The attribution model selection (FD, META, EXTERNAL) is applied via GET /PUT /events/{eid}/attribution_model. See Wave — Attribution.

Common gotchas

The “edit one published cluster” endpoint is POST /campaigns_setup (plural, no {eid} in URL, eid goes in the body). It is not the same as PUT /setup_processes/{eid}. They are two different lifecycle stages.
There is no setupId in the URL. Concurrent edits across tabs race on the same row. The reference webapp uses a module-level AbortController to drop stale PUTs.
The endpoint expects the full setup_process. Sending a partial resets unspecified fields to defaults.
UTILIZATION, ROAS, VISIBILITY, LINK_CLICKS — not tickets, revenue, reach.