Billing
Credit-based metering across compute, orchestration, model calls, and storage. Theazo tracks every resource consumed — per user, per session, per run — so you can enforce budgets, fire threshold alerts, and re-bill your users with a single API call.
{ amount: number, currency: string } where amount is integer cents. 500 = $5.00. Never strings.Credit system
Theazo uses a credit system where 1 credit = $0.01. Credits are dollar-denominated, not unit-denominated — there is no conversion math specific to model calls or compute events. Credits are purchased in advance and drawn down as your agents run. All API responses report costs as credits and as the { amount, currency } pair.
// Credits are interchangeable with cents in all SDK responses
const usage = await theazo.billing.getCreditBalance()
console.log(usage.credits) // 4823 — credits remaining
console.log(usage.cost) // { amount: 4823, currency: 'usd' } ($48.23)
console.log(usage.consumedToday) // { amount: 177, currency: 'usd' } ($1.77 today)Rate card
Four billing categories. Costs accrue automatically regardless of which mode you operate in. BYOI compute is not billed by Theazo — see the BYOI section.
Plan tiers
Credits are included in each plan. Overages draw from your credit balance. You can purchase additional credit packs at any time from the dashboard or via the billing API.
Budget hierarchy
Budgets enforce spending limits at four levels. Each level constrains everything below it. When a budget is exhausted the enforcement happens atomically via Redis INCRBY — there is no race window.
Setting budgets
import { Theazo } from 'theazo'
const theazo = new Theazo({ apiKey: 'th_live_...' })
// Platform-wide budget — caps all usage across every user
await theazo.billing.setBudget({
maxCost: { amount: 50000, currency: 'usd' }, // $500/day across platform
period: 'day',
})
// Per-user budget — caps a specific end-user's spending
await theazo.billing.setUserBudget('user_alice', {
maxCost: { amount: 2000, currency: 'usd' }, // $20/month per user
period: 'month',
})
// Session-level limit — caps a single session
const session = await theazo.sessions.forUser('user_alice', {
limits: {
maxCost: { amount: 500, currency: 'usd', period: 'day' }, // $5/day
maxAgents: 3,
maxComputeMinutes: 60,
},
})
// Run-level limit — caps one agent.run() call
const result = await agent.run('Summarize this codebase', {
maxCost: { amount: 50, currency: 'usd' }, // $0.50 max per run
})Threshold alerts
Theazo fires budget webhooks at 50%, 80%, and 100% of any budget level. Use these to warn users before they hit their limit, or to trigger auto top-ups. The budget.exhausted event fires when the limit is reached and agents are paused.
budget.thresholdFires at 50% and 80% of any budget level. Includes level, userId (if user budget), current spend, and limit.
budget.exhaustedFires when a budget is fully consumed. All running agents in scope are paused. Resume by updating the limit.
// Example budget.threshold payload
{
"event": "budget.threshold",
"level": "user", // 'platform' | 'user' | 'session' | 'run'
"userId": "user_alice",
"threshold": 80, // percent consumed
"consumed": { "amount": 1600, "currency": "usd" },
"limit": { "amount": 2000, "currency": "usd" },
"period": "month"
}
// Example budget.exhausted payload
{
"event": "budget.exhausted",
"level": "user",
"userId": "user_alice",
"consumed": { "amount": 2001, "currency": "usd" },
"limit": { "amount": 2000, "currency": "usd" },
"agentsPaused": ["agt_x1", "agt_x2"]
}After a budget is exhausted, update the limit and call session.resume() to unpause agents.
// Raise the budget and resume paused agents
await theazo.billing.setUserBudget('user_alice', {
maxCost: { amount: 5000, currency: 'usd' },
period: 'month',
})
const session = await theazo.sessions.forUser('user_alice')
await session.resume()Environment separation
Agent runs are tagged with an environment. Development runs are free and do not count toward credits. Staging and production runs are billed separately so you can track them independently.
// Tag runs with environment
const session = await theazo.sessions.forUser('user_alice', {
environment: 'dev', // 'dev' | 'staging' | 'production'
})
// Or at run time
await agent.run('Test task', { environment: 'staging' })BYOI cost split
When you bring your own infrastructure (BYOI), the usage response includes a cost split: theazoBilled is what Theazo charges you (orchestration only), and providerDirect is what your BYOI provider charges you directly. The two never overlap.
const usage = await theazo.usage.forUser('user_alice', {
period: { start: '2026-06-01', end: '2026-06-30' },
})
console.log(usage.cost.theazoBilled) // { amount: 140, currency: 'usd' } — orchestration fees
console.log(usage.cost.providerDirect) // { amount: 870, currency: 'usd' } — E2B/Fly/etc. billed direct
console.log(usage.cost.total) // { amount: 1010, currency: 'usd' } — full picture for pass-through billingCost webhooks
When an agent run completes, Theazo fires agent.run.completed with a full cost breakdown. Use this to update your own billing records or trigger downstream re-billing flows — no polling required.
agent.run.completedFires when a run finishes (completed, failed, or cancelled). Includes full cost breakdown: compute, model, storage, orchestration, and total.
workflow.run.completedSame as above but for workflow runs. Also includes per-step cost breakdown.
// agent.run.completed payload
{
"event": "agent.run.completed",
"agentId": "agt_abc123",
"runId": "run_xyz789",
"userId": "user_alice",
"status": "completed",
"cost": {
"compute": { "amount": 15, "currency": "usd" }, // sandbox runtime
"model": { "amount": 42, "currency": "usd" }, // model tokens
"storage": { "amount": 2, "currency": "usd" }, // snapshot size
"orchestration": { "amount": 8, "currency": "usd" }, // control plane
"total": { "amount": 67, "currency": "usd" },
"theazoBilled": { "amount": 67, "currency": "usd" },
"providerDirect":{ "amount": 0, "currency": "usd" } // 0 = managed compute
},
"duration": 43, // seconds
"environment": "production"
}Credit balance
Credit enforcement is Redis-local for low latency. Theazo reconciles with Dodo Payments asynchronously. The local counter can drift by at most one usage event before reconciliation fires. Enterprise customers can configure synchronous reconciliation.
// Get current balance
const balance = await theazo.billing.getCreditBalance()
console.log(balance.credits) // 4823
console.log(balance.cost) // { amount: 4823, currency: 'usd' }
console.log(balance.planIncluded) // { amount: 5000, currency: 'usd' }
console.log(balance.overageUsed) // { amount: 0, currency: 'usd' }
console.log(balance.renewsAt) // '2026-07-01T00:00:00Z'Per-user usage
Query usage for any individual end-user. Use this to build usage meters in your product UI, enforce per-user limits, or generate itemized invoices for your users.
// Query usage for one user
const usage = await theazo.usage.forUser('user_alice', {
period: { start: '2026-06-01', end: '2026-06-30' },
})
console.log(usage.cost.total) // { amount: 1010, currency: 'usd' }
console.log(usage.computeMinutes) // 202
console.log(usage.modelCalls) // 87
console.log(usage.activeAgents) // 0 (point-in-time)
console.log(usage.cost.theazoBilled) // { amount: 140, currency: 'usd' }
console.log(usage.cost.providerDirect) // { amount: 870, currency: 'usd' }
// Session-level usage
const session = await theazo.sessions.forUser('user_alice')
const sessionUsage = await session.usage()
console.log(sessionUsage.cost) // { amount: 234, currency: 'usd' }
console.log(sessionUsage.computeMinutes) // 47
console.log(sessionUsage.activeAgents) // 2
console.log(sessionUsage.modelCalls) // 38Usage export
Export usage data for re-billing your users. Three formats: Stripe-compatible line items (ready to attach to invoices), CSV for spreadsheets, and raw JSON. All exports can be grouped by user, session, provider, or day.
// Stripe-compatible — attach directly to Stripe invoice line items
const stripe = await theazo.usage.export({
format: 'stripe',
period: { start: '2026-06-01', end: '2026-06-30' },
})
// CSV — one row per session with cost breakdown columns
const csv = await theazo.usage.export({
format: 'csv',
period: { start: '2026-06-01', end: '2026-06-30' },
groupBy: 'user',
})
// JSON — full usage records with metadata
const json = await theazo.usage.export({
format: 'json',
period: { start: '2026-06-01', end: '2026-06-30' },
groupBy: 'day', // 'user' | 'session' | 'provider' | 'day'
environment: 'production',
})unit_amount (integer cents), quantity (1), and description fields. Pass them directly to the Stripe invoiceitem.create API.API reference
/v1/billing/balanceGet current credit balance, plan details, and overage usage.
Response
CreditBalanceExample
curl https://api.theazo.com/v1/billing/balance \
-H "Authorization: Bearer th_live_..."/v1/billing/budgetSet or update the platform-level budget. Fires budget.threshold webhooks at 50% and 80%.
Parameters
maxCostCostrequired{ amount: number, currency: string } — integer cents.periodstringrequired'day' | 'week' | 'month' | 'total'Response
BudgetExample
curl -X POST https://api.theazo.com/v1/billing/budget \
-H "Authorization: Bearer th_live_..." \
-H "Content-Type: application/json" \
-d '{ "maxCost": { "amount": 50000, "currency": "usd" }, "period": "month" }'/v1/billing/budget/users/:userIdSet or update a per-user spending budget.
Parameters
maxCostCostrequired{ amount: number, currency: string } — integer cents.periodstringrequired'day' | 'week' | 'month' | 'total'Response
BudgetExample
curl -X POST https://api.theazo.com/v1/billing/budget/users/user_alice \
-H "Authorization: Bearer th_live_..." \
-H "Content-Type: application/json" \
-d '{ "maxCost": { "amount": 2000, "currency": "usd" }, "period": "month" }'/v1/usagePlatform-wide usage summary. Filterable by period and environment.
Parameters
startstringISO 8601 start date. Default: start of current month.endstringISO 8601 end date. Default: now.environmentstring'dev' | 'staging' | 'production'. Default: all.Response
UsageSnapshotExample
curl "https://api.theazo.com/v1/usage?start=2026-06-01&environment=production" \
-H "Authorization: Bearer th_live_..."/v1/usage/by-user/:userIdUsage for a single end-user across all their sessions. Includes theazoBilled/providerDirect split.
Parameters
startstringISO 8601 start date.endstringISO 8601 end date.Response
UserUsageSnapshotExample
curl "https://api.theazo.com/v1/usage/by-user/user_alice?start=2026-06-01" \
-H "Authorization: Bearer th_live_..."/v1/usage/dailyDaily aggregated usage for charts. Returns an array of { date, cost, computeMinutes, modelCalls } objects.
Parameters
startstringrequiredISO 8601 start date.endstringrequiredISO 8601 end date.environmentstringFilter by environment.Response
DailyUsage[]Example
curl "https://api.theazo.com/v1/usage/daily?start=2026-06-01&end=2026-06-30" \
-H "Authorization: Bearer th_live_..."/v1/usage/exportExport usage data as Stripe line items, CSV, or JSON. Supports groupBy for aggregation.
Parameters
formatstringrequired'stripe' | 'csv' | 'json'periodobjectrequired{ start: string, end: string } — ISO 8601 dates.groupBystring'user' | 'session' | 'provider' | 'day'environmentstringFilter by environment. Default: production.Response
ExportResultExample
curl -X POST https://api.theazo.com/v1/usage/export \
-H "Authorization: Bearer th_live_..." \
-H "Content-Type: application/json" \
-d '{
"format": "stripe",
"period": { "start": "2026-06-01", "end": "2026-06-30" },
"groupBy": "user"
}'SDK method reference
theazo.billing.getCreditBalance()Promise<CreditBalance>Current credits, plan-included amount, overage used, and renewal date.theazo.billing.setBudget(opts)Promise<Budget>Set or update platform-level budget. Fires threshold webhooks at 50% and 80%.theazo.billing.setUserBudget(userId, opts)Promise<Budget>Set or update a per-user spending limit. Scoped to one end-user across all sessions.theazo.usage.forUser(userId, opts?)Promise<UserUsageSnapshot>Usage for one user: cost split (theazoBilled/providerDirect), computeMinutes, modelCalls.theazo.usage.export(opts)Promise<ExportResult>Export usage as Stripe line items, CSV, or JSON. Groupable by user/session/provider/day.theazo.usage.daily(opts)Promise<DailyUsage[]>Daily aggregated usage. Useful for charts and dashboards.theazo.usage.byProvider(opts)Promise<ProviderUsage[]>Usage broken down by compute provider: E2B, Fly, Docker, etc.session.usage()Promise<UsageSnapshot>Current session consumption: cost, computeMinutes, activeAgents, modelCalls.session.limits()Promise<LimitsSnapshot>Configured limits alongside current usage for each dimension.session.updateLimits(limits)Promise<void>Update limits on a live session. Partial updates supported. Takes effect immediately.session.resume()Promise<void>Resume agents paused by a budget exhaustion event after limits have been raised.