Skip to content

Coffee

Query campaign-level audience and engagement data scoped to your authorized networks. Two endpoints are available: a paginated JSON endpoint for app integration and a streaming CSV endpoint for bulk export.


GET /api/v1/coffee

Returns Coffee rows as paginated JSON.

Query parameters

ParameterTypeRequiredDefaultDescription
fromISO 8601 date or datetimeYesStart of the time window (inclusive). Date-only (e.g. 2026-04-01) is treated as UTC midnight.
toISO 8601 date or datetimeYesEnd of the time window (exclusive). Date-only is treated as UTC midnight.
site_idinteger or integer[]NoFilter by one or more site IDs. Each value must be a positive integer.
limitintegerNo1000Number of rows to return. Must be a positive integer between 1 and 5000. Values outside this range are rejected.
sortasc | descNoascSort direction. Must be exactly asc or desc — any other value is rejected.
afterISO 8601 datetimeNoCursor pagination. Returns rows strictly after this timestamp. Use the next_after value from the previous response. Takes priority over offset. Must be a valid ISO 8601 timestamp (not date-only).
offsetintegerNoOffset pagination. Number of rows to skip. Must be a non-negative integer. Use for random page access. Ignored if after is provided.

Date range limit

The fromto range cannot exceed 31 days.

Pagination modes

Two pagination modes are supported. Cursor mode is preferred for sequential traversal of large datasets.

Pass next_after from the previous response as after= on the next request. When next_after is null, you have reached the last page.

Page 1: ?from=...&to=...&limit=5000
Page 2: ?from=...&to=...&limit=5000&after=<next_after from page 1>
Page 3: ?from=...&to=...&limit=5000&after=<next_after from page 2>

Offset-based (random page access)

Use offset to jump directly to any page. Note that performance may degrade at large offsets.

Page 1: ?from=...&to=...&limit=5000&offset=0
Page 3: ?from=...&to=...&limit=5000&offset=10000

Response 200

json
{
  "status": true,
  "message": "Success",
  "data": {
    "total": 84320,
    "limit": 5000,
    "next_after": "2026-04-02T08:44:21.000Z",
    "count": 5000,
    "rows": [
      {
        "POP_TYPE": "ACTIVE",
        "PLAY_REASON": "SCHEDULED",
        "CAMPAIGN_ID": 101,
        "CAMPAIGN_NAME": "Spring Campaign",
        "TARGET_STRATEGY_ID": 5,
        "STRATEGY_NAME": "Daytime",
        "MEDIA_PLAYER_NAME": "Player A",
        "DETAILID": 9001,
        "EVENT_ID": "evt-abc123",
        "TITLE": "Promo 30s",
        "DISPLAY_TITLE": "Spring Promo",
        "PLAYOUT": 30.0,
        "DT_START_SITE_TZ": "2026-04-02T08:00:00.000Z",
        "DT_END_SITE_TZ": "2026-04-02T08:00:30.000Z",
        "WATCHERID": 500,
        "SITE_ID": 1,
        "SITE_NAME": "Sydney CBD",
        "NETWORK_ID": 7,
        "NETWORK_NAME": "Acme Network",
        "IS_IMPRESSION": 1,
        "IS_VIEW": 1,
        "IS_WATCHED": 0,
        "ATTENTION": 82.50,
        "WATCH_TIME": 14.25
      }
    ]
  }
}

Last page

When next_after is null and count is less than limit, you have reached the last page.

Client loop example

js
let after = null;
let allRows = [];

do {
  const params = new URLSearchParams({ from, to, limit: 5000 });
  if (after) params.set('after', after);

  const { data } = await fetch(`/api/v1/coffee?${params}`, {
    headers: { Authorization: `Bearer ${token}` }
  }).then(r => r.json());

  allRows.push(...data.rows);
  after = data.next_after;
} while (after !== null);

Errors

CodeDescription
400Missing from/to; invalid ISO 8601 value; range exceeds 31 days; from is not before to; limit out of range; invalid offset, sort, site_id, or after value
401Invalid or expired token; X-Network-Name header value is not authorized by the token; site_id does not belong to the caller's networks
403Token does not have access to any networks
500Internal server error

GET /api/v1/coffee/download

Streams Coffee rows as a CSV file. Designed for bulk data export — memory usage on the server is constant regardless of result size.

Query parameters

ParameterTypeRequiredDefaultDescription
fromISO 8601 date or datetimeYesStart of the time window (inclusive). Date-only (e.g. 2026-04-01) is treated as UTC midnight.
toISO 8601 date or datetimeYesEnd of the time window (exclusive). Date-only is treated as UTC midnight.
site_idinteger or integer[]NoFilter by one or more site IDs. Each value must be a positive integer.
limitintegerNoMaximum rows to include. Must be a positive integer between 1 and 5000. If omitted, all matching rows are streamed.
offsetintegerNo0Number of rows to skip. Must be a non-negative integer.

Unsupported parameters

after and sort are not supported for CSV download — the endpoint returns 400 if either is provided.

Postman

Postman displays CSV as raw text. To save the file, click Save Response → Save to a file after the request completes. For large exports, use curl instead.

curl example

API Base URL: https://prod-gcp.services.api.viana.ai

bash
curl -H "Authorization: Bearer <token>" \
  "<API_BASE_URL>/api/v1/coffee/download?from=2026-04-01&to=2026-04-07" \
  -o coffee.csv

Response

Returns a text/csv file download with filename coffee_YYYYMMDD_YYYYMMDD.csv. The first row is always the header row containing all available field names — even if there are no matching data rows.

Field reference

The CSV export includes the following fields:

ColumnTypeDescription
POP_TYPEstringPopulation type
PLAY_REASONstringReason for playback
CAMPAIGN_IDnumberCampaign identifier
CAMPAIGN_NAMEstringCampaign name
TARGET_STRATEGY_IDnumberTargeting strategy ID
STRATEGY_NAMEstringTargeting strategy name
MEDIA_PLAYER_NAMEstringMedia player name
DETAILIDnumberDetail record ID
EVENT_IDstringEvent identifier
TITLEstringContent title
DISPLAY_TITLEstringDisplay title
PLAYOUTfloatPlayout duration (seconds)
DT_START_SITE_TZtimestampPlayout start time (site timezone)
DT_END_SITE_TZtimestampPlayout end time (site timezone)
WATCHERIDnumberWatcher identifier
DELTA_IDarrayDelta IDs
SITE_TIMESTAMP_SITE_TZtimestampSite timestamp (site timezone)
WATCH_TIMESTAMP_SITE_TZ_DETAILSarrayWatch start timestamps
WATCH_TIMESTAMP_END_SITE_TZ_DETAILSarrayWatch end timestamps
DETECTION_TIMESTAMP_SITE_TZtimestampDetection start (site timezone)
DETECTION_TIMESTAMP_END_SITE_TZtimestampDetection end (site timezone)
REIDstringRe-identification token
START_TIMEarrayStart time details
GENDERstringDetected gender
AGEstringDetected age
AGE_CATEGORYstringAge category
GENDER_AGE_CATEGORYstringCombined gender+age category
MOODstringDetected mood
DISTANCEarrayDistance measurements
ATTENTIONnumberAttention score (0–100)
DURATIONfloatDetection duration (seconds)
WATCH_TIMEnumberTotal watch time (seconds)
IS_IMPRESSIONnumber1 if impression, 0 otherwise
DURATION_IMPRESSIONnumberImpression duration (seconds)
IS_GLANCEnumber1 if glance, 0 otherwise
DURATION_GLANCEnumberGlance duration (seconds)
IS_VIEWnumber1 if view, 0 otherwise
DURATION_VIEWnumberView duration (seconds)
IS_VIEW_THROUGHnumber1 if view-through, 0 otherwise
DURATION_VIEW_THROUGHnumberView-through duration (seconds)
IS_WATCHEDnumber1 if watched, 0 otherwise
NETWORK_IDnumberNetwork identifier
NETWORK_NAMEstringNetwork name
SITE_IDnumberSite identifier
SITE_NAMEstringSite name
LOCATION_IDnumberLocation identifier
LOCATION_NAMEstringLocation name
DEVICE_IDnumberDevice identifier
DEVICE_NAMEstringDevice name
FEEDER_IDnumberFeeder identifier
FEEDER_NAMEstringFeeder name
SUBSCRIPTION_NAMEstringSubscription name
SITE_TZstringSite timezone
DEVICE_TZstringDevice timezone
TIME_RANGE_SITE_TZstringTime range label (site timezone)
MONTHstringMonth label
DT_ONLY_SITE_TZdateDate only (site timezone)
HOUR_SITE_TZstringHour label (site timezone)
DAY_SITE_TZstringDay label (site timezone)
IS_BUSINESSHOURbooleanTrue if within business hours
SILVER_STAGE_TIMESTAMPtimestampSilver stage processing time
STREAM_STAGE_TIMESTAMPtimestampStream stage processing time
SF_DELTA_IDstringSnowflake delta ID

Errors

CodeDescription
400Missing from/to; invalid ISO 8601 value; range exceeds 31 days; from is not before to; limit out of range; invalid offset or site_id; after or sort provided
401Invalid or expired token; X-Network-Name header value is not authorized by the token; site_id does not belong to the caller's networks
403Token does not have access to any networks
500Internal server error