Usage
Metered usage for ONE calendar month, for the tenant the credential belongs to (never a query parameter). `org`, `period`, `used` and `mode` are always present; the plan block below it is present whenever the org resolves to a billing record, which is every legitimate tenant (a new workspace starts on `starter`). `status`, `has_billing_account` and `billing_state` are billing data: they are sent only to a credential holding `billing:manage` (owners and admins, and a workspace's own non-member API key), never to a member's or viewer's key or a widget token.
Properties
| Name | Type | Description |
|---|---|---|
| org | string | The tenant the usage belongs to, derived from the authenticated credential. |
| period | string | UTC calendar month, `YYYY-MM`. |
| used | integer | metered domain connections this period |
| mode | string | The Stripe key mode the control plane is running against; empty when billing is unconfigured. |
| plan | object | |
| plan_name | string | The plan's display name, e.g. `Growth`. |
| quota | integer | The plan's included domain connections for ONE billing MONTH (`DomainsPerYear` ceiling-divided by 12; `0` = unlimited). Compare `used` against this. `limit` carries the identical value. |
| limit | integer | Alias of `quota`, carrying the identical value. This schema declared `limit` while the handler emitted only `quota`; rather than break either reader, both are emitted. Prefer `quota` in new code. |
| metered | boolean | `true` on tiers priced for overage (`growth`, `enterprise`). It carries NO enforcement meaning; it describes pricing only. Read `hard_cap` for the plan's refusal policy and `quota_enforced` for whethe |
| hard_cap | boolean | Whether this PLAN refuses connections past `quota` (`402 quota_exceeded`) rather than allowing and recording them as overage. `true` only on the entry tiers: `starter` ($10 a month) and the retired `f |
| quota_state | string | The server's classification of `used` against `quota`. `approaching` means at or past 80% of quota; `at_limit` means `used >= quota`. Always `ok` on an unlimited plan (`quota <= 0`). |
| quota_enforced | boolean | Whether an over-quota connection would actually be refused with `402 quota_exceeded` right now. True only when the plan's `hard_cap` is set AND the deployment enables enforcement. A client cannot infe |
| remaining | integer | `quota - used`, floored at `0`. Omitted entirely on an unlimited plan, where no remainder is meaningful. |
| status | string | Subscription status mirrored from Stripe, e.g. `active`, `past_due` (empty for a workspace that has not subscribed). Owners and admins only. |
| has_billing_account | boolean | `true` when a Stripe customer exists for the org, i.e. the billing portal is available. Owners and admins only. |
| billing_state | object |
JSON Schema
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"$id": "https://artifacts.apis.io/customdomain-ai/json-schema/customdomain-ai-usage-schema.json",
"title": "Usage",
"description": "Metered usage for ONE calendar month, for the tenant the credential belongs to (never a query parameter). `org`, `period`, `used` and `mode` are always present; the plan block below it is present whenever the org resolves to a billing record, which is every legitimate tenant (a new workspace starts on `starter`). `status`, `has_billing_account` and `billing_state` are billing data: they are sent only to a credential holding `billing:manage` (owners and admins, and a workspace's own non-member API key), never to a member's or viewer's key or a widget token.",
"x-generated": "2026-11-10",
"x-method": "derived",
"x-generator": "derive-json-schema.py",
"x-source": "openapi/customdomain-ai-billing-api-openapi.yml#/components/schemas/Usage",
"type": "object",
"required": [
"org",
"period",
"used",
"mode"
],
"properties": {
"org": {
"type": "string",
"description": "The tenant the usage belongs to, derived from the authenticated credential."
},
"period": {
"type": "string",
"description": "UTC calendar month, `YYYY-MM`."
},
"used": {
"type": "integer",
"description": "metered domain connections this period"
},
"mode": {
"type": "string",
"enum": [
"test",
"live",
""
],
"description": "The Stripe key mode the control plane is running against; empty when billing is unconfigured."
},
"plan": {
"$ref": "#/$defs/PlanId"
},
"plan_name": {
"type": "string",
"description": "The plan's display name, e.g. `Growth`."
},
"quota": {
"type": "integer",
"description": "The plan's included domain connections for ONE billing MONTH (`DomainsPerYear` ceiling-divided by 12; `0` = unlimited). Compare `used` against this. `limit` carries the identical value."
},
"limit": {
"type": "integer",
"description": "Alias of `quota`, carrying the identical value. This schema declared `limit` while the handler emitted only `quota`; rather than break either reader, both are emitted. Prefer `quota` in new code."
},
"metered": {
"type": "boolean",
"description": "`true` on tiers priced for overage (`growth`, `enterprise`). It carries NO enforcement meaning; it describes pricing only. Read `hard_cap` for the plan's refusal policy and `quota_enforced` for whether a `402` is possible right now. Never branch on this field."
},
"hard_cap": {
"type": "boolean",
"description": "Whether this PLAN refuses connections past `quota` (`402 quota_exceeded`) rather than allowing and recording them as overage. `true` only on the entry tiers: `starter` ($10 a month) and the retired `free`. Every larger tier (`startup`, `premium`, `growth`, `enterprise`) is `false` and is never refused at quota. The refusal reaches the tenant's own end users through the embedded widget, so it is worded neutrally for them. Independent of the deployment's `BILLING_ENFORCE_QUOTA`; combine the two via `quota_enforced`."
},
"quota_state": {
"type": "string",
"enum": [
"ok",
"approaching",
"at_limit"
],
"description": "The server's classification of `used` against `quota`. `approaching` means at or past 80% of quota; `at_limit` means `used >= quota`. Always `ok` on an unlimited plan (`quota <= 0`)."
},
"quota_enforced": {
"type": "boolean",
"description": "Whether an over-quota connection would actually be refused with `402 quota_exceeded` right now. True only when the plan's `hard_cap` is set AND the deployment enables enforcement. A client cannot infer the second half, which is why this is served rather than derived. On every paid tier it is `false` at any usage level. A tenant may therefore be `at_limit` with `quota_enforced: false` (over the line with nothing refused), so never treat `at_limit` alone as \"blocked\". Always `false` on an unlimited plan."
},
"remaining": {
"type": "integer",
"description": "`quota - used`, floored at `0`. Omitted entirely on an unlimited plan, where no remainder is meaningful."
},
"status": {
"type": "string",
"description": "Subscription status mirrored from Stripe, e.g. `active`, `past_due` (empty for a workspace that has not subscribed). Owners and admins only."
},
"has_billing_account": {
"type": "boolean",
"description": "`true` when a Stripe customer exists for the org, i.e. the billing portal is available. Owners and admins only."
},
"billing_state": {
"$ref": "#/$defs/BillingState"
}
},
"$defs": {
"BillingState": {
"type": "string",
"description": "A workspace's billing state, evaluated from its record and the clock. `trialing` and `active` are a running Stripe subscription; `past_due` is a failed payment Stripe is still retrying (nothing is refused); `grace` is a legacy Free workspace (or an operator extension) inside its grace period; `legacy_free` is a Free workspace whose grace has not started; `comped` is an operator comp; `blocked` and `canceled` refuse new connections (`402 billing_required`) while live domains keep working. A new workspace (`blocked`, reason `setup_required`) is refused only once its first domain is connected: see `first_domain_free`.",
"enum": [
"trialing",
"active",
"past_due",
"grace",
"blocked",
"comped",
"canceled",
"legacy_free"
]
},
"PlanId": {
"type": "string",
"description": "`free` is retired: legacy workspaces still carry it until they subscribe, and it cannot be bought or assigned.",
"enum": [
"starter",
"startup",
"growth",
"premium",
"enterprise",
"free"
]
}
}
}
Work with this as data
Every JSON Schema here is available over the APIs.io API and to AI agents over MCP.
MCP server
One button, every client — Claude, Cursor, VS Code and the rest.
https://apis.io/mcp
Tools for schemas
4 MCP tools reach this
find_json_schemasBrowse and filter every JSON Schema in the catalog.apis_io_searchSTART HERE — APIs, providers and tags for one query, each with its total.resolveTurn a domain, URL or GitHub org into the provider it belongs to.find_cohortsEvery scored population of providers in the catalog.
Call it yourself
curl for this page
curl "https://apis.io/api/v1/json-schemas/customdomain-ai-usage"
curl "https://apis.io/api/v1/json-schemas?limit=25"
Calls without X-API-Key need no key. Calls with it need a paid plan — get a key.
Get an API key
Free tier, no form to fill in. Signing in shares your email address with us — we store it to create your key and to recognise you if you sign in with another provider. See our Privacy Policy and Terms.
A second provider on the same verified email joins the account you already have.