Reporting API best practices
Understand the Tapjoy Offerwall Reporting API endpoint, request structure, and error handling to effectively access accurate user acquisition data.
Read time 5 minutesLast updated 5 hours ago
The Reporting API enables advertisers and publishers to access reporting data from the Tapjoy platform and manage their Offerwall content, using the GraphQL query language. For more information on GraphQL, refer to GraphQL's official website.
Use the API Explorer to help build your queries. Select the book icon in the top left corner to expand the Documentation Explorer and find information on the fields and metrics you can use in your queries.

API endpoint
The Reporting API has a single endpoint:
https://api.tapjoy.com/graphql
The endpoint remains the same for every operation.
Communicating with the API
When you have an access token, you can make requests to the API. To form a request, send a JSON-encoded body in an HTTP POST, whether you're executing a query or a mutation.
Refer to the following example request:
POST /graphqlHost: api.tapjoy.comAuthorization: Bearer <OAuth Token>{ "query": "query { user { firstName } }"}
Set time increments and ranges
Use the argument to bucket insights:
timeIncrementValue | Result |
|---|---|
| ALL | A single aggregated value for the whole range. Applies when you omit the argument. |
| DAILY | One value per day. |
| HOURLY | One value per hour. Valid only for ranges shorter than 1 week. |
| MONTHLY | One value per month. |
NONEargumentLiteralsIncompatibleALLThe requested range must be at least 1 hour and at most 3 months, and can be no earlier than 2 years ago. Timestamps must be ISO 8601 with a timezone (). The API rejects bare dates.
from2024-03-01T00:00:00ZWorking with errors
You can encounter the following categories of errors when you use the API:
- Server and network errors
- Authentication and authorization errors
- Query syntax errors
- Data validation errors
To integrate your system properly, consider how it handles each of these categories of errors.
Each of the following error categories uses this query for context:
query { user { firstName lastName }}
Server and network errors
Occasionally you might encounter unrecoverable server or network errors with the API. In these cases, the API returns the HTTP status code for the scenario you encounter. For example, if a problem with the API prevents queries from executing, you receive an HTTP response with a 500 status code.
To handle this scenario, retry the request with exponential back-off.
Limitations
The Reporting API has certain protections in place to prevent excessive or abusive API calls. If your integration exceeds these limits, contact your Tapjoy account manager or support to understand how to optimize your integration or how to increase your limits.
The following examples apply to both advertiser and publisher integrations.
Data retention
The Reporting API can access the last two years of data.
Pagination
When you query a paginated type, you must follow these rules:
- Supply a or
firstargument.last - Request no more than 100 nodes in a single page.
Omitting the pagination argument returns a 422 error. For example, traversing the connection requires ; without or fails. The same requirement applies to other paginated connections, such as .
campaignscampaigns(first: N)advertiser { campaigns { ... } }firstlastadSetsIf you exceed the maximum value, the API truncates the results and ignores your or argument.
firstlastFor example:
{ advertiser { adSets(first: 50) { edges { node { id name ads(first: 50) { edges { node { id name } } } } } } }}
The previous query returns a maximum of 50 ad sets, each with a maximum of 50 ads.
To paginate through collections, you must provide an or argument to control where to start the page. For example:
afterbefore{ advertiser { adSets(first: 50, after: "Mg==") { edges { node { id name } } pageInfo { endCursor hasNextPage } } }}
The previous query returns a maximum of 50 ad sets, starting at the cursor position . The value that an earlier query returns determines that position. Pagination is complete when is .
Mg==endCursorhasNextPagefalseFor more information about pagination, refer to the GraphQL documentation.
Call complexity
To pass schema validation, a Marketing API call must not exceed 10,000 calls, where a call is a request for a resource. Because GraphQL lets you combine multiple calls into a single query, the API calculates the total number of calls for a query before it executes that query.
The number of calls is roughly equivalent to the number of resources you select from the result, such as campaigns, ad sets, ads, apps, and insights.
Consider the same example:
{ advertiser { adSets(first: 50) { # <= 50 calls edges { node { id name ads(first: 50) { # <= 50 calls edges { node { id name } } } } } } }}
In this example, you request up to 50 ad sets at a time, and up to 50 ads for each ad set.
To calculate the total number of calls:
50 = 50 ad sets+50 x 50 = 2500 ads = 2550 calls
There's no rate limit for the number of calls per hour.
Insights complexity
Reporting insights that you query at any level incur an additional complexity cost that the previous calculation doesn't reflect. The API adds 1 call to the calculation for each day you query.
Consider the following example:
{ advertiser { # 50 calls adSets(first: 50) { edges { node { id name # 7 calls insights(timeRange: {from: "2024-03-01T00:00:00Z", until: "2024-03-08T00:00:00Z"}) { timestamps reports { country impressions conversions spend } } } } } }}
In this example, you request up to 50 ad sets at a time, and 7 days' worth of reporting data across 3 metrics and 1 segment for each ad set.
To calculate the total number of calls:
50 = 50 ad sets+50 x 7 = 350 insights = 400 calls