Skip to main content
Pick the endpoint that matches how you store and report the data. For soundlinks without a campaign, see Soundlink metrics.

Overview

GET /v1/campaigns/{campaignId}/metrics/overview POST /v1/campaigns/metrics/overview/batch Campaign-level totals for a date range: listeners (attributed new / Super Listeners), total_listeners (distinct new + returning in the window), streams, followers, delivery (impressions, ad_clicks, link_clicks), spend (spend_media, spend_total, fees), and efficiency metrics (cpl, cpf, streams_per_listener). One row per campaign per request window. cpl uses listeners. streams_per_listener uses total_listeners, matching dashboard S/L. total_listeners is not the sum of daily breakdown total_listeners — returning listeners count once in the overview window. Use for dashboards, executive summaries, and quick health checks. Not broken down by country or track. CTR fields (ctr_linkclick, ctr_adclick) are on breakdown rows, not overview. Per-day new_listeners / returning_listeners are on breakdown (and engagement), not overview. Overview only adds the window-level total_listeners. For many campaigns in one sync, use the batch route. Same totals and date query as the single GET, up to 50 campaignIds per request (one rate-limit unit). Unauthorized or unknown IDs are omitted from data.items. Batch reads must be enabled for your organization — otherwise the route returns 404.

Creatives

GET /v1/campaigns/{campaignId}/metrics/creatives POST /v1/campaigns/metrics/creatives/batch Lifetime performance for one campaign, grouped by background video. Each group has a children array of variants (caption, language, track, and the audio cut as timestamp_start_ms / timestamp_end_ms). Both timestamps are null when the cut is not a ready sound. Two cuts of the same track stay separate. This is a snapshot — startDate and endDate return 400. Maps to the Creatives tab in Soundlink Insights. Spend is omitted until media spend and fees can be split. Ratios use the same lifetime basis as that tab. Requires metrics:read.
The batch route returns the same lifetime groups per authorized campaign (data.items[].campaignId + creatives). Up to 50 IDs, one rate-limit unit, omit unauthorized IDs, and the same rules as overview batch. Do not send dates.
See the API Reference for the response shape.

Creative daily

GET /v1/campaigns/{campaignId}/metrics/creative-daily (paginated) One row per day and current Meta ad creative: spend_media, impressions, followers, and cpf. spend_media excludes fees. cpf is spend_media / followers for that row, and null when followers is zero. Across days, divide summed spend by summed followers. Separate from Creatives, which is a lifetime snapshot grouped by background video and rejects dates. Each ad is counted once, from its latest smartlink row. startDate and endDate are optional and inclusive. Omit both for every day that has rows. Page size defaults to 50 and maxes at 500.

Breakdown (by country)

GET /v1/campaigns/{campaignId}/metrics/breakdown (paginated) GET /v1/campaigns/{campaignId}/metrics/breakdown/export (JSONL) Per-day, per-country rows (campaign_country_daily v1.1). Primary key: (provider, account_id, report_date, campaign_id, country_code) Each row includes listeners (new), new_listeners, returning_listeners, and total_listeners. streams_per_listener is streams / total_listeners for that row. schema_version is 1.1. On track campaigns (campaign_target_type = track), each row also includes campaign_target_isrc and campaign_target_spotify_track_id. Use campaign_target_spotify_track_id to join with partner track catalogs when ISRC is unavailable. Maps to the Countries tab in Soundlink Insights. Use for geo reporting and daily warehouse loads by territory.

Engagement (by track)

GET /v1/campaigns/{campaignId}/metrics/engagement (paginated) GET /v1/campaigns/{campaignId}/metrics/engagement/export (JSONL) Per-day, per-track rows (campaign_engagement_daily v1.0). Primary key: (provider, account_id, report_date, campaign_id, engagement_context, country_code, engaged_spotify_track_id) Engagement counts plays from listeners who connected Spotify through the campaign’s soundlink, starting when they connected. Use it for catalog spillover and playlist performance while the campaign runs. Listening history is synced while the campaign is active. After it ends, sync stops for listeners whose only connection is that campaign, so post-campaign days are partial and usually drop sharply — do not read that drop as listeners leaving. Engagement rows also include campaign_target_isrc and campaign_target_spotify_track_id for the promoted track when campaign_target_type = track. engagement_context values:
  • catalog — same-artist spillover and direct plays on track campaigns
  • playlist — per-track performance inside the promoted playlist
Filter with ?engagementContext=catalog or playlist when you only need one slice. Playlist engagement rows include playlist_position — the track’s 1-based slot on the campaign playlist for that report_date. See Playlist position.

Retention (by cohort)

GET /v1/campaigns/{campaignId}/metrics/retention Cohort retention for the campaign’s soundlink. Rows use the same soundlink_cohort_retention_daily v1.0 shape as Soundlink metrics, with one row per cohort date and no pagination. startDate and endDate filter the cohort date (inclusive). If you omit both, a recent window ending today is used. A range that is too wide returns 400 invalid_query_parameter. If the campaign isn’t in your organization, the response is 404 campaign_not_found. If it has no linked soundlink, the response is 404 not_found. Requires metrics:read.

Weekly retention (by cohort week)

GET /v1/campaigns/{campaignId}/metrics/retention-weekly Same item shape as Soundlink weekly retention. Cohort weeks are anchored on the campaign start in UTC, not on a calendar Monday. startDate and endDate filter cohort_week (inclusive). If you omit both, a recent window ending today is used. A range that is too wide returns 400 invalid_query_parameter. If the campaign isn’t in your organization, the response is 404 campaign_not_found. Requires metrics:read.

Data mutability

Rows for a given report_date can change for up to 7 days after the date closes (delayed Meta and Spotify events). Re-fetch and re-ingest on the primary key — it is idempotent.

Listeners vs streams

On breakdown and engagement rows, do not sum listeners or total_listeners across days — the same listener can appear on multiple report_date rows. That sum will not match overview total_listeners. Summing streams within a day is safe; across days it counts repeat listens.

Listening insights

GET /v1/campaigns/{campaignId}/listening-insights/{insight} What connected listeners went on to play: other artists, playlist catalog follow-through, or the stream split. The window is fixed by the listening graph. There is no startDate or endDate. Calls often take 30–50 seconds, so use a client timeout of at least 120 seconds. Requires metrics:read. See Listening insights.

Next

Warehouse connector · Playlist position · JSONL exports · API Reference