Publisher API

Errors

HTTP status codes and JSON bodies for the Publishers API.

Two response shapes

Survey endpoint (POST /api/v1/publishers/surveys)

Most responses use:

{
  "requestStatus": "true" | "false",
  "message": "…"
}

Success with offers uses requestStatus: "true". Failures use "false" plus message.

Authentication failures

Missing or invalid API keys return HTTP 401 with a top-level error field (not requestStatus):

{
  "error": "Invalid or missing API key. Use Authorization: Bearer <key> or X-API-Key header."
}

HTTP status codes

StatusMeaningWhat you should do
200Request processedRead requestStatus and hasSurveys
400Invalid request body, validation error, or redirect URLs not configuredFix payload or portal config
401Invalid or missing API keyCheck authentication
403Key valid but account not permittedSign in to the portal once and create the key there; otherwise contact support
404Unknown appId for your organizationVerify appId in the portal
405Wrong HTTP methodUse POST only
429Rate limit exceeded for your API keyWait for Retry-After seconds, then retry (see Rate limits)
502Survey matching temporarily unavailableRetry with exponential backoff
504Gateway timeout in front of the API (rare)Retry with exponential backoff

Common HTTP 400 causes

message (or symptom)CauseFix
App redirect URLs … must all be configuredComplete, Screen-out, Cancelled URL or signing secret missingFill in all four under Apps → your app → Settings
Missing required field: panelistId although you sent itpanelistId or appId sent as a numberSend strings: "12345"
Invalid locale / Invalid countrye.g. de_DE, german, or de as country"locale": "de-DE", "country": "DE"
Invalid profileDetails.ageAge sent as a string or outside 0–130"age": 34 (JSON number)
age / gender missing (from 2026-10-06)Required profile fields not sentAlways send both; before that date the response carries a profile_fields_required_soon warning instead
expected a single object, not an array"profileDetails": [ { … } ]Send one object: "profileDetails": { … }

A slow survey match does not return 504 (since 2026-09-23): after 5 seconds the API answers 200 with hasSurveys: false, empty surveys / partlySurveys and a warnings entry with code: "matching_timeout". Treat it like an empty wall and call again on the next page view.

Common validation messages (HTTP 400)

MessageCause
Missing required field: …Required JSON field missing or empty
Invalid locale / Invalid countryFormat not accepted
Redirect URLs messageComplete, screen-out, or cancelled URL or signing secret missing
Unknown appId or app does not belong to your organization.Wrong appId

Rate limits

Each API key may make 600 requests per minute across all /api/v1/publishers/* endpoints. The limit is a fixed one-minute window, counted per API key (not per IP), so one partner can never throttle another.

Over the limit, the API returns HTTP 429 with the standard body and a Retry-After header (seconds until the window resets):

HTTP/1.1 429 Too Many Requests
Retry-After: 23
Content-Type: application/json

{
  "requestStatus": "false",
  "message": "Rate limit exceeded. Max 600 requests per minute per API key — retry after the Retry-After interval."
}

Recommendations:

  • Call the surveys endpoint once per panelist page view and cache the response client-side for the session — do not poll.
  • Honour Retry-After before retrying; treat a burst of 429s as a signal to add client-side throttling.
  • If you legitimately need more than 600 requests/minute, contact support with your expected peak rate.

Method not allowed (HTTP 405)

{
  "error": "Method not allowed",
  "allowed": ["POST"]
}

Retries

StatusRetry?
400, 401, 403, 404No — fix the request or configuration
429Yes — after the Retry-After interval
502, 504Yes — backoff and retry
200 + hasSurveys: falseNot an error — show empty state
200 + warnings[].code: "matching_timeout"Show empty state; call again on the next page view (no tight retry loop)

Profiling URL (legacy)

profilingUrl may appear in a 200 success body for backward compatibility. It is deprecated — do not rely on it in new integrations. Show offer entryLink values instead; base profile questions are collected inline when the panelist starts an offer.

If you still open profilingUrl, treat it like entryLink: HTTPS only, no secrets embedded.

Logging

Log HTTP status, requestStatus, and message so you can quote them to support. Do not log full API keys or signing secrets.

On this page