Usage API guide
The Billing Usage API provides comprehensive, invoice-aligned usage data for programmatic cost tracking and reporting. This guide covers authentication, query optimization, and advanced integration patterns.
The Billing Usage API requires OAuth 2.0 authentication for all requests. All API requests must be authenticated using an OAuth access token.
Before generating a token, create an OAuth application in OneConsole to acquire your client credentials. The application type depends on the scope of the endpoints you intend to query:
- Organization-level applications: Required if you're querying Billing Group-level endpoints.
- Account-level applications: Required if you're querying Account level endpoints.
Ensure your application is explicitly configured with the following permission scope:
twilio/billing-insights/usage/read
This scope grants read access to billing usage data at the appropriate level (organization or account).
Obtain an access token by submitting a request to the token endpoint using your client credentials. Include this access token in the Authorization header of every API request:
Authorization: Bearer YOUR_OAUTH_ACCESS_TOKEN
The Billing Usage API provides data you can reconcile with your invoice. It includes:
- Structured JSON payloads: Use
POSTrequests with JSON request bodies to combine date, product, aggregation, and pagination filters for precise query customization. - Invoice-aligned product taxonomy: The
productCategoryparameter aligns with the standardized, multi-level product taxonomy used in the Console and billing statements. - Separated usage and price data: Response payloads clearly separate usage measurements and costs into distinct, structured objects for easier integration.
- Predictable query ranges: A custom date range can cover up to 365 days. Use explicit dates instead of legacy endpoints (such as
/Todayand/Alltime). - Token-based pagination: Use
nextTokenfrom the response metadata to page through results, replacing legacy page indexing. - Standardized data freshness: Data updates in predictable 24-hour batches, which keeps intra-month reporting consistent.
Billing Group usage data is retrieved through the Billing Usage API using two complementary methods:
| Method | URL endpoint | Description |
|---|---|---|
| POST | https://billing.twilio.com/v2/Public/Usage/BillingGroups/{billingGroupId}/Records | Initiate a query with filter parameters in the request body. |
| GET | https://billing.twilio.com/v2/Public/Usage/BillingGroups/{billingGroupId}/Records | Paginate results using pageToken and pageSize parameters. |
Replace {billingGroupId} with the specific billing_group_ string retrieved from the Console. This ensures the API correctly identifies the billing entity for which you are requesting records.
POST https://billing.twilio.com/v2/Public/Usage/BillingGroups/{billingGroupId}/Records
The request body is a JSON object containing your filter parameters:
1{2"startOn": "2025-01-01",3"endOn": "2025-01-31",4"productCategory": "sms",5"aggregationPeriod": "DAILY",6"pageSize": 1007}
Precise data retrieval makes analysis more effective. By using request parameters, you can isolate specific cost drivers, filter by product categories, and define exact timeframes.
Info
The timePeriod parameter is an alternative to startOn and endOn. Do not use them in the same request.
| Parameter | Type | Description |
|---|---|---|
startOn | Date (YYYY-MM-DD) | Filter usage from this date (inclusive). Maximum range is 365 days. |
endOn | Date (YYYY-MM-DD) | Filter usage to this date (inclusive). Maximum range is 365 days. |
timePeriod | Enum: YESTERDAY, THIS_MONTH, LAST_MONTH, THIS_YEAR | A predefined filter as an alternative to custom start and end dates. |
productCategory | String | Isolate usage data for a specific Twilio product category (for example, sms, voice, video). |
aggregationPeriod | Enum: DAILY, MONTHLY | Define how records are grouped within the requested range. |
pageSize | Integer | Limit the number of items returned in a single response. Range is 1-1000. |
pageToken | String | Token from the previous response's meta.nextToken field to retrieve the next page of results. |
The aggregationPeriod is a critical tool for financial granularity:
- DAILY: Identify specific usage spikes or trends within a month. Vital for spotting anomalies and understanding daily cost drivers. Use daily aggregation when investigating unexpected charges or tracking hour-to-hour changes.
- MONTHLY: Provides a high-level executive view of spend for period-over-period analysis.
Warning
Queries are currently limited to a maximum date range of one month. If you attempt to request data spanning more than one month, the system will return an error or incomplete results. This is a temporary limitation while Twilio works to enhance system capabilities. Use timePeriod shortcuts (such as THIS_MONTH or LAST_MONTH) for month-long queries, or break larger date ranges into monthly chunks.
The Usage API returns structured output that maps technical usage metrics directly to costs. The response shows what was used, when it was used, and the associated price.
The API returns records with the following properties:
| Property | Type | Description |
|---|---|---|
asOf | Date (YYYY-MM-DD) | The latest date/time for the records, formatted in UTC. This represents when the data snapshot was taken. |
updatedOn | Date (YYYY-MM-DD) | The date the data was last updated, formatted in UTC. The latest value is typically the day before the request date because the current day's data is still being computed. |
productName | String | A human-readable name of the Twilio product (for example, United States-Outbound-LC-MMS). |
productCategory | String | The standardized category for the product (for example, united-states-outbound-lc-mms). |
startOn | Date (YYYY-MM-DD) | The first date for which usage is included (UTC). |
endOn | Date (YYYY-MM-DD) | The last date for which usage is included (UTC). |
usage | Object | Contains amount (numeric volume) and unit (metric type, such as segments, minutes, or messages). |
price | Object | Contains amount (total cost in the billing currency) and currency (ISO 4217 code, such as USD, GBP, EUR). |
1{2"updatedOn": "2025-01-31",3"records": [4{5"productName": "United States-Outbound-LC-MMS",6"productCategory": "united-states-outbound-lc-mms",7"startOn": "2025-01-01",8"endOn": "2025-01-31",9"usage": {10"amount": 66505,11"unit": "segments"12},13"price": {14"amount": 100.5,15"currency": "USD"16}17},18{19"productName": "United States-Outbound-SMS",20"productCategory": "united-states-outbound-sms",21"startOn": "2025-01-01",22"endOn": "2025-01-31",23"usage": {24"amount": 1250000,25"unit": "messages"26},27"price": {28"amount": 625.0,29"currency": "USD"30}31}32],33"meta": {34"key": "records",35"pageSize": 100,36"previousToken": "eyJzdGFydE9uIjoiMjAyNS0wMS0wMSIsImVuZE9uIjoiMjAyNS0wMS0zMSIsInBhZ2UiOiIxIiwicGFnZVNpemUiOiIxMDAifQ",37"nextToken": "eyJzdGFydE9uIjoiMjAyNS0wMS0wMSIsImVuZE9uIjoiMjAyNS0wMS0zMSIsInBhZ2UiOiIyIiwicGFnZVNpemUiOiIxMDAifQ"38}39}
For organizations with high volume usage, managing pagination is critical:
The meta section of the response contains:
pageSize: The number of records returned in the current response.previousToken: Token to retrieve the previous page (if available).nextToken: Token to retrieve the next page (if available).
To iterate through all records without missing data:
- Execute your initial query with your desired filters.
- Process the records returned in the
recordsarray. - If
meta.nextTokenis present, make another request with the same filters. Add"pageToken": "NEXT_TOKEN"to the request body, replacing NEXT_TOKEN with the value ofmeta.nextToken. - Repeat until
meta.nextTokenis not present or is null.
This token-based pagination replaces legacy page-number indexing and lets you traverse large datasets reliably.
1// First request2{3"startOn": "2025-01-01",4"endOn": "2025-01-31",5"pageSize": 1006}78// Response includes meta.nextToken910// Second request with pagination11{12"startOn": "2025-01-01",13"endOn": "2025-01-31",14"pageSize": 100,15"pageToken": "eyJzdGFydE9uIjoiMjAyNS0wMS0wMSIsImVuZE9uIjoiMjAyNS0wMS0zMSIsInBhZ2UiOiIyIiwicGFnZVNpemUiOiIxMDAifQ"16}
Usage data is updated in batches and may be up to 24 hours behind current activity. The latest available updatedOn value is typically the day before the request date because the current day's data is still being computed. This standardized cadence ensures every record reflects verified billing data, eliminating data drift and intra-day reconciliation discrepancies.
Warning
Usage API data is an estimate. Actual billed usage is reflected on your invoice or usage statement after month-end. Use the Usage API for real-time cost tracking and internal reporting, but reconcile with your official invoice for final billing records.