Aggregate cost across a time window
const url = 'https://example.com/v1/cost/aggregate?groupBy=example&scopeKind=tenant&inherit=true';const options = {method: 'GET', headers: {Authorization: 'Bearer <token>'}};
try { const response = await fetch(url, options); const data = await response.json(); console.log(data);} catch (error) { console.error(error);}curl --request GET \ --url 'https://example.com/v1/cost/aggregate?groupBy=example&scopeKind=tenant&inherit=true' \ --header 'Authorization: Bearer <token>'Primary consumer path for dashboards. groupBy is required (comma-separated dimensions from the closed set); time range is required (both from and to, or both omitted for the default last-30-days window echoed back in timeRange). Filters compose on top of the time window. ?scopeKind + ?scopeId + ?inherit narrow the aggregate to a specific scope — reconciles byte-for-byte with the same scoped /records list.
Authorizations
Section titled “Authorizations”Parameters
Section titled “Parameters”Query Parameters
Section titled “Query Parameters”Comma-separated list of dimensions to aggregate over. Each value must be one of agentId | runId | category | providerId | day | month | tenant | conversationId. Duplicates collapse.
ISO 8601 timestamp; records with occurredAt >= from. Required on /v1/cost/aggregate (or both endpoints omitted for default last-30-days window).
ISO 8601 timestamp; records with occurredAt <= to. Required on /v1/cost/aggregate (or both endpoints omitted for default last-30-days window).
Filter to a specific category (llm.inference, tool.invocation, storage.write, sandbox.exec, …). Exact match.
Filter records to this provider id (exact match).
Filter records to this agent id (exact match).
Filter records to this run id (exact match).
Filter records to this conversation id (exact match).
Discriminator for the ?scopeKind + ?scopeId + ?inherit triplet. Tenant carries no id (implicit from session); org/project require scopeId.
Optional scope discriminator. If absent, no scope filter is applied.
Required IF scopeKind is org or project. MUST be absent if scopeKind=tenant (tenant is implicit from the session). Malformed combinations return 400 scope-invalid.
Default true. false = literal-at-this-scope only (admin/audit view). Load-bearing for policy/config-scoped resources (mcp-endpoints); documented no-op for content-scoped resources (agents/flows/tools/…).
Responses
Section titled “Responses”Aggregate rollup.
object
object
One entry per requested groupBy dimension. null = distinct “unattributed” bucket (records had no value for that dimension).
object
object
The dimensions the server actually grouped by — echoed so callers can round-trip the response without re-parsing the request URL.
Example
{ "groupBy": [ "agentId" ]}Missing / malformed groupBy, unknown dimension, missing one endpoint of the time range, or from > to.
object
object
Stable machine-readable discriminant. Values match domain error codes (see docs/API-ROUTE-CONVENTIONS.md §4.3).
Optional, kind-specific.
object
Server-assigned request id; also echoed via X-Request-Id header.
Examplegenerated
{ "error": { "code": "example", "message": "example", "details": {}, "requestId": "example" }}Missing / malformed / expired / revoked bearer token.
object
object
Stable machine-readable discriminant. Values match domain error codes (see docs/API-ROUTE-CONVENTIONS.md §4.3).
Optional, kind-specific.
object
Server-assigned request id; also echoed via X-Request-Id header.
Examplegenerated
{ "error": { "code": "example", "message": "example", "details": {}, "requestId": "example" }}