Skip to main content

AI Budget

The per-user AI credit-budget endpoint. Tenant-wide usage reporting (summaries, monthly trends, top consumers) lives in the Usage & Credits section.

Moved endpoints

The old GET /api/ai-usage and GET /api/ai-overview admin endpoints have been removed. Tenant-wide consumption is now served by GET /api/usage, GET /api/usage/monthly, and GET /api/usage/top-consumers.

GET /api/ai-budget

Return the authenticated user's AI credit-budget status: their effective usage profile, month-to-date consumption against any per-actor cap, and the tenant credit pool. This is a credit budget, not a weekly or per-session budget.

Authentication: Required (AI access)

Pre-blocks: ai.verify

The ai.verify pre-block (verifyAiEnabledAndAllowed) gates the route before the handler runs:

  • It throws 400 ("AI is not enabled on the system") when the tenant's aiEnabled master switch is off.
  • It throws 403 when the user has no AI access (no usage profile and not a superuser).

There is no 402 from this route; the 402 Payment Required enforcement happens on AI requests that would exceed a cap, budget, or the pool, not on reading budget status.

Response fields:

FieldTypeDescription
configuredbooleanWhether AI is configured. false until the entitlement cache holds a valid License Manager JWT. Clients use this to block sends and show an upgrade CTA.
byokbooleanWhether the tenant uses its own provider keys, read straight off the signed license. When true, AI calls do not draw from the credit pool.
creditsRequiredbooleantrue when credit gating applies to this actor (credits are metered and enforced).
slushActivebooleantrue when the paid pool is empty and consumption is drawing on the internal safety buffer.
profileobject | nullThe user's effective usage profile (null if none applies). Carries name, slug, creditCapPerMonth, allowedModelTiers, and features.
monthlyobjectMonth-to-date consumption (see below).
poolobjectThe tenant credit pool (see below).

monthly object:

FieldTypeDescription
creditsUsednumberCredits consumed by this user month-to-date.
creditCapinteger | nullThe profile's monthly cap (null = unlimited, 0 = hard stop).
percentUsednumberPercent of the monthly cap consumed.
resetsAtdateWhen the monthly cap resets (start of next month).
isUnlimitedbooleantrue when configured with no monthly cap.

pool object:

The public projection of the tenant credit balance. The internal slush and creditsRequired keys are stripped from the pool. An unconfigured pool serializes as { remaining: null, included: null, overageRate: null }, with no used key.

FieldTypeDescription
includedinteger | nullCredits included in the tenant's plan.
usedintegerCredits consumed against the pool. Present only on a configured pool.
remaininginteger | nullCredits remaining in the pool.
overageRatenumber | nullPer-credit overage rate once the included pool is exhausted.

Response:

When AI is enabled but the entitlement cache holds no License Manager JWT yet, the route returns the "AI enabled but not yet configured" budget state: configured: false, a profile derived from defaults, and an empty (all-null) pool.

Get my AI budget statusGET /api/ai-budget
GET /api/ai-budget returns the authenticated user's credit-budget status, NOT a weekly/session budget. Real top-level shape is { configured, byok, creditsRequired, slushActive, profile, monthly, pool } — the docs page omits `creditsRequired` (true when credit gating applies). `monthly` is { creditsUsed, creditCap, percentUsed, resetsAt, isUnlimited } and `pool` is publicPool(creditBalance) with the internal `slush` and `creditsRequired` keys stripped (so an unconfigured pool serializes as { remaining:null, included:null, overageRate:null }, with no `used` key). `configured` is false until the entitlement cache holds a License Manager JWT; `byok` is read straight off the signed license.
Response · 200
{
"_links": {
"self": {
"href": "https://informer.example.com/api/ai-budget"
}
},
"configured": false,
"byok": false,
"creditsRequired": true,
"slushActive": false,
"profile": {
"name": "Standard",
"slug": "standard",
"creditCapPerMonth": 5000,
"allowedModelTiers": [
"everyday",
"advanced"
],
"features": []
},
"monthly": {
"creditsUsed": 0,
"creditCap": 5000,
"percentUsed": 0,
"resetsAt": "2026-01-15T16:20:00.000Z",
"isUnlimited": false
},
"pool": {
"remaining": null,
"included": null,
"overageRate": null
}
}
Captured from the API examples test suite; ids and timestamps are normalized.
AI must be enabled

When the tenant has not enabled AI (the aiEnabled master switch is off), the route answers 400 "AI is not enabled on the system", not 402 or 403.

Budget when AI is disabledGET /api/ai-budget
GET /api/ai-budget is gated by the `ai.verify` pre-block. When the tenant has not enabled AI (the `aiEnabled` master switch is off), the route answers 400 "AI is not enabled on the system" — not 402/403.
Response · 400
{
"statusCode": 400,
"error": "Bad Request",
"message": "AI is not enabled on the system"
}
Captured from the API examples test suite; ids and timestamps are normalized.
Credit metering

AI requests are metered in credits derived from model token usage and the License Manager rate card. Enforcement happens before each request: see the enforcement flow. A request that would exceed a cap, budget, or the pool returns 402 Payment Required with a machine-readable code. Reading budget status with this endpoint never returns 402.