Skip to content
Coritan Docs

Client API: Usage and budgets

What your services used and cost: a month by service and day, hourly rows, credit activity, budgets, billing events and questions about a charge.

View as Markdown

What your services used and cost: a month by service and day, hourly rows, credit activity, budgets, billing events and questions about a charge.

Base URL: https://api.coritan.com/api/v1. Paths below are complete.

To try these requests in the browser, open the interactive Client API reference.

Method Path Summary
GET /api/v1/billing/budgets The account's budget and each deployment's
PUT /api/v1/billing/budgets Set the account's budget or a deployment's
DELETE /api/v1/billing/budgets Remove the account's budget or a deployment's
POST /api/v1/billing/charge-queries Ask us about one hour of usage
GET /api/v1/billing/compute-usage What the account's compute used and cost in a month, by product group
GET /api/v1/billing/credit/forecast How many days the credit lasts
GET /api/v1/billing/credit/ledger Every credit debit, with the service and hours it paid for
POST /api/v1/billing/estimate What a mix of products would cost a month
GET /api/v1/billing/events Price changes, switches and caps applied
GET /api/v1/billing/invoices/{invoice_id}/usage An invoice's usage lines, opened to their hours and meters
GET /api/v1/billing/usage/rows The hourly rows behind a month of usage
GET /api/v1/billing/usage/summary A month of usage by service, meter and day

The account's budget and each deployment's

Section titled The account's budget and each deployment's

GET /api/v1/billing/budgets

The monthly budgets you set: one across everything the account uses (the account budget) and one for each deployment, with what counts against each this month.

A budget sends an email at 80% and at 100% (thresholds). At 100% its policy applies: block holds back previews, bursts, builds and use past a free amount, and pause stops every instance until the budget is raised or the month turns. The account budget counts every service billed by use, a virtual machine's included, and its policy applies to all of them. A deployment budget covers web services, static sites, game servers and databases, which are all deployments. A virtual machine has no deployment of its own, so only the account budget covers it. Object Storage has its own budget, set under /billing/object-storage/{id}/budget.

available lists the deployments billed by use that have no budget yet, for a form that adds one. This is the platform account's own budget; an organization's owner sets its usage budget under /api/v1/orgs/{org_slug}/billing/usage-cost.

Authentication: an access token, sent as Authorization: Bearer <token>.

Status Meaning
200 Success.

Fields of a 200 response:

Field Type Description
currency string
month string
account BudgetOut or null The budget across everything the account uses; null when there is none
account.scope string account for the budget across everything, deployment for one deployment's
account.deployment_uuid string or null The deployment's uuid; null for the account budget
account.service_id integer or null
account.name string Account, or the deployment's name
account.group string or null app_deployment or container_apps, for a deployment
account.monthly_limit string The budget for a month, in the account's currency, two decimal places
account.policy string What happens at 100%: block holds back extras, pause stops every instance
account.used string What counts against it this month
account.reached boolean
account.thresholds array of integer The percentages an alert email is sent at
deployments array of BudgetOut Each deployment's own budget
deployments[].scope string account for the budget across everything, deployment for one deployment's
deployments[].deployment_uuid string or null The deployment's uuid; null for the account budget
deployments[].service_id integer or null
deployments[].name string Account, or the deployment's name
deployments[].group string or null app_deployment or container_apps, for a deployment
deployments[].monthly_limit string The budget for a month, in the account's currency, two decimal places
deployments[].policy string What happens at 100%: block holds back extras, pause stops every instance
deployments[].used string What counts against it this month
deployments[].reached boolean
deployments[].thresholds array of integer The percentages an alert email is sent at
available array of BudgetCandidate Deployments billed by use that have no budget yet
available[].deployment_uuid string
available[].service_id integer or null
available[].name string
available[].group string
policies array of string What a budget can do at 100%
thresholds array of integer The percentages an alert email is sent at

Set the account's budget or a deployment's

Section titled Set the account's budget or a deployment's

PUT /api/v1/billing/budgets

Set a monthly budget, or change it: the account's (scope account) or one deployment's (scope deployment with its deployment_uuid). Setting a budget above what is spent lifts what it held.

Answers 404 for a deployment this account does not pay for, 409 for one billed by its own service's plan, which a budget would never apply to, 422 for an amount that is not more than 0 and at most 1000000 with two decimal places, for a scope or policy this list does not name and for a deployment budget with no deployment_uuid, and 429 after 30 changes in an hour. Every change is in the account's activity log.

Authentication: an access token, sent as Authorization: Bearer <token>.

application/json (required)

Field Type Required Description
scope string no account or deployment
deployment_uuid string or null no The deployment, for scope deployment
monthly_limit number or string yes An amount in the account's currency, for example 50.00
policy string no At 100%: block holds back previews, bursts, builds and overage, pause stops every instance
Status Meaning
200 Success.
422 The request is not valid. detail lists each problem.

Fields of a 200 response:

Field Type Description
scope string account for the budget across everything, deployment for one deployment's
deployment_uuid string or null The deployment's uuid; null for the account budget
service_id integer or null
name string Account, or the deployment's name
group string or null app_deployment or container_apps, for a deployment
monthly_limit string The budget for a month, in the account's currency, two decimal places
policy string What happens at 100%: block holds back extras, pause stops every instance
used string What counts against it this month
reached boolean
thresholds array of integer The percentages an alert email is sent at

Remove the account's budget or a deployment's

Section titled Remove the account's budget or a deployment's

DELETE /api/v1/billing/budgets

Remove a budget and lift what it held. Answers 204 whether or not there was one, 404 for a deployment this account does not pay for, 422 for a deployment budget with no deployment_uuid and 429 after 30 changes in an hour.

Authentication: an access token, sent as Authorization: Bearer <token>.

Name In Type Required Description
scope query string no account or deployment Default: account.
deployment_uuid query string or null no The deployment, for scope deployment
Status Meaning
204 Success.
422 The request is not valid. detail lists each problem.

Ask us about one hour of usage

Section titled Ask us about one hour of usage

POST /api/v1/billing/charge-queries

Ask support about a charge. Name the service, the meter and the hour, and say what looks wrong. We find that hour's usage row, open a support conversation that names it (the service, meter, hour, quantity and amount) and answer with the conversation's id. Support sees the row with your message.

The hour is read in UTC and rounded down to the hour. Answers 404 when this account has no usage for that service, meter and hour, 422 for a meter this list does not name or a blank message, and 429 after 10 questions in an hour. The question is in the account's activity log.

Authentication: an access token, sent as Authorization: Bearer <token>.

application/json (required)

Field Type Required Description
service_id integer yes The service the hour was for
hour string (date-time) yes The hour in question, in UTC (2026-09-21T10:00:00). Minutes are ignored.
meter string yes The meter's key, for example memory_gib_hours
message string yes What looks wrong
Status Meaning
201 Success.
422 The request is not valid. detail lists each problem.

Fields of a 201 response:

Field Type Description
id integer
status string
service_id integer
hour string
meter string
amount string What the hour cost
ticket_id integer or null The support conversation we opened
ticket_number integer or null Its number, as support lists it

What the account's compute used and cost in a month, by product group

Section titled What the account's compute used and cost in a month, by product group

GET /api/v1/billing/compute-usage

What the account's compute used and cost in a month, by product group.

The three groups are App Deployment (app_deployment), Cloud Compute (cloud_compute) and Container Apps (container_apps: game servers and databases), each with the number of its services billed by use, what it totals so far and a meters list: the quantity in the meter's unit, what the month's included amounts covered (included), what was billable, its amount and its forecast to the end of the month. Only services billed by use count, so a free server and a service that keeps a flat price are not in it.

pools shows the included amounts against use: the web pool is every account's and covers App Deployment, the server pool covers Cloud Compute and Container Apps together and is active only with the Paid plan (paid_plan). Each of its amounts has the used quantity, the included quantity and the share of it used (null when nothing is included, and above 1 once use passes it). The web pool's three data out meters share one amount, egress_gb.

forecast is the month's cost if each running service keeps the pace it has used the meters at (a service needs a day of use first), after the pool's included amounts. forecast_basis is pace for this month, final for an earlier one, whose forecast is its cost, and none in the first hours of a month, when every forecast is null. through is the hour the figures are settled to. spend_limit is the account's own monthly limit with what counts against it, or null.

Answers 422 for a month that is not YYYY-MM.

Authentication: an access token, sent as Authorization: Bearer <token>.

Name In Type Required Description
month query string or null no YYYY-MM; this month when left out
Status Meaning
200 Success.
422 The request is not valid. detail lists each problem.

How many days the credit lasts

Section titled How many days the credit lasts

GET /api/v1/billing/credit/forecast

How long the credit lasts at the pace of the last 7 days of hourly use: the daily rate, the days left and the date it runs out. Hourly use is what rated usage and flat hourly charges took from credit; renewals and one-off payments do not count.

daily_rate, days_left and runs_out_on are null when there was no hourly use in those days, and for an account that pays by invoice, which credit never runs out for (pays_by_invoice). A service stops when credit cannot pay for its hours, and a top-up starts the hourly services that stopped for it.

Authentication: an access token, sent as Authorization: Bearer <token>.

Status Meaning
200 Success.

Fields of a 200 response:

Field Type Description
currency string
balance string The credit left
pays_by_invoice boolean True for an account that pays by invoice, which credit never runs out for
basis_days integer The days of use the rate is taken from
daily_rate string or null What hourly use takes from credit a day; null when there was none
days_left number or null How many days the credit lasts at that rate; null when it has no rate
runs_out_on string or null The date it runs out, YYYY-MM-DD; null when it has no rate or is more than ten years away

Every credit debit, with the service and hours it paid for

Section titled Every credit debit, with the service and hours it paid for

GET /api/v1/billing/credit/ledger

Every time credit was used, newest first: the amount, the balance after, the service it was for and, for usage, the hours and meters it paid for. Hourly debits are here, which the credit balance's recent list does not show.

A debit that paid rated usage has kind usage and the first and last hour it covers (from, to), the hours and the meters. A flat hourly charge has hourly. Credit you added is not listed. Page with before. Answers 422 for a limit above 200. This is the platform account's own credit; an organization's owner reads its credit under /api/v1/orgs/{org_slug}/billing.

Authentication: an access token, sent as Authorization: Bearer <token>.

Name In Type Required Description
limit query integer no Debits to return Default: 50.
before query integer or null no The next_before of the last page, to read the next one
Status Meaning
200 Success.
422 The request is not valid. detail lists each problem.

Fields of a 200 response:

Field Type Description
currency string
balance string
items array of DebitOut
items[].id integer
items[].amount string What was taken, as a positive amount
items[].balance_after string
items[].description string
items[].kind string usage for rated hours, hourly for a flat hourly charge and other for anything else
items[].created_at string
items[].service DebitServiceOut or null The service the debit was for, when it was for one
items[].invoice_id integer or null
items[].from string or null The first hour the debit paid for
items[].to string or null The last hour the debit paid for
items[].hours integer How many hours the debit paid for
items[].meters array of string
next_before integer or null Pass it as before to read the next page; null at the end

What a mix of products would cost a month

Section titled What a mix of products would cost a month

POST /api/v1/billing/estimate

Price a month of App Deployment, game servers, Cloud Compute, Object Storage, SMTP Relay, mail and a domain, from the same price book as the order quote and the public estimator. Nothing is ordered or written.

Each component names a product and the inputs it reads (a server's size, hours_per_day and cpu_share, a web service's instances, memory_gib, requests_millions and egress_gb, and so on). The free amounts are those of a month nothing has used yet, and the first component to use a meter takes them. A server on a Free plan adds the Paid plan. account is your own plan unless you pass another to compare.

Answers 422 for a product, plan or cycle this list does not name, a number out of range, more than 20 components, or a size the price book does not sell (the answer names the sizes that exist). Amounts are in US dollars to the cent.

Authentication: an access token, sent as Authorization: Bearer <token>.

application/json (required)

Field Type Required Description
account string or null no The plan the estimate assumes: free, pro, business. Your own plan when left out.
cycle string or null no Billing cycle for the prices that have one: monthly, annually. monthly when left out.
location string or null no A location code, which sets the price of data out
components array of EstimateComponent yes The products to price, at most 20
components[].product string yes One of: app_deployment, game_server, cloud_compute, object_storage, smtp_relay, mail, domain
components[].label string or null no A name for the line, shown back to you
components[].size string or null no A server's size, for example cx4 or rx-2
components[].instances integer or null no Copies that run
components[].hours_per_day number or null no Hours a day it runs; 0 is switched off
components[].memory_gib number or null no Memory each instance holds, in GiB
components[].cpu_vcpu number or null no CPU each instance uses on average, in vCPUs
components[].cpu_share number or null no The share of a server's vCPUs in use, from 0 to 1
components[].requests_millions number or null no Millions of requests a month
components[].egress_gb number or null no GB sent out a month
components[].storage_gb number or null no GB stored in Object Storage
components[].class_a_millions number or null no Millions of Object Storage writes and lists a month
components[].class_b_millions number or null no Millions of Object Storage reads a month
components[].emails_per_month integer or null no Emails SMTP Relay sends a month
components[].mailboxes integer or null no Mailboxes, for Mail Hosting
components[].tld string or null no A domain's ending without the dot, for example com
Status Meaning
200 Success.
422 The request is not valid. detail lists each problem.

Fields of a 200 response:

Field Type Description
currency string USD
lines array of object Each priced meter: key, group, label, quantity, included, billable, unit, rate and amount
subtotal string The lines together, to the cent
plan_cost string The Paid plan, when the estimate needs it and the account does not have it
total string subtotal plus plan_cost
notes array of string What the estimate assumes
unpriced array of any Products the price book has no price for. The total leaves them out.

Price changes, switches and caps applied

Section titled Price changes, switches and caps applied

GET /api/v1/billing/events

What changed in how the account is billed, newest first: a price change (announced before it takes effect), a service moved between billing terms, a budget cap applied, a budget alert, a suspension for no credit and its resume. Each event has a title that says it in a sentence and the detail behind it. Page with before. Answers 422 for a limit above 100. These are the platform account's own events; an organization's owner reads its own under /api/v1/orgs/{org_slug}/billing/usage-cost.

Authentication: an access token, sent as Authorization: Bearer <token>.

Name In Type Required Description
limit query integer no Events to return Default: 20.
before query integer or null no The next_before of the last page, to read the next one
Status Meaning
200 Success.
422 The request is not valid. detail lists each problem.

Fields of a 200 response:

Field Type Description
items array of BillingEventOut
items[].id integer
items[].kind string What happened: price_change, switch, cap_applied, budget_alert, suspension or resume
items[].title string A sentence that says it
items[].detail object or null The figures behind it
items[].service_id integer or null
items[].app_id integer or null
items[].created_at string
next_before integer or null Pass it as before to read the next page; null at the end

An invoice's usage lines, opened to their hours and meters

Section titled An invoice's usage lines, opened to their hours and meters

GET /api/v1/billing/invoices/{invoice_id}/usage

The usage lines of one invoice, each with its meter, its unit, the period it covers and the number of hours it adds up. The invoice answer shows a line as a description and a total; this opens it.

Send ?format=csv or Accept: text/csv for the hourly rows the invoice bills (the columns of GET /billing/usage/rows). Hours that were charged from credit before an invoice was made are not on the invoice and are not in it.

Answers 404 for an invoice that is not the account's, and an invoice with no usage lines answers an empty list. This is the platform account's own invoice; an organization's owner reads its customers' usage at /api/v1/orgs/{org_slug}/billing/usage-cost.

Authentication: an access token, sent as Authorization: Bearer <token>.

Name In Type Required Description
invoice_id path integer yes The invoice's id
format query string or null no csv for the hourly rows the lines add up from
Status Meaning
200 JSON, or the invoice's hourly rows as CSV
422 The request is not valid. detail lists each problem.

Fields of a 200 response:

Field Type Description
invoice_id integer
currency string
total string The usage lines together
lines array of InvoiceUsageLineOut
lines[].item_id integer
lines[].description string
lines[].service_id integer or null
lines[].service string or null The deployment's name, or the server's host name
lines[].meter string or null
lines[].unit string What quantity counts, for example GiB-hours
lines[].quantity string
lines[].rate string The line's amount divided by its quantity
lines[].amount string
lines[].from string or null The first hour the line covers, in UTC
lines[].to string or null The end of the last hour the line covers, in UTC
lines[].hours integer or null How many rated hours the line adds up

The hourly rows behind a month of usage

Section titled The hourly rows behind a month of usage

GET /api/v1/billing/usage/rows

The hourly rows that a month's usage adds up from, newest hour first: the hour, the service, the meter, the quantity, the rate, the amount and its state. Filter by service, meter or state.

Send ?format=csv or Accept: text/csv for a file with the columns hour, service_id, service, meter, unit, quantity, included, billable, rate, amount, currency and status. A CSV holds at most 100000 rows: page with offset for more, and the X-Total-Rows header says how many match. A cell that a spreadsheet would run as a formula is written as text.

Answers 422 for a month that is not YYYY-MM, for a meter or state this list does not name, and for a JSON limit above 1000. A service that is not the account's, or is not billed by the second, has no rows. This is the platform account's own usage; an organization's owner reads what its customers cost at /api/v1/orgs/{org_slug}/billing/usage-cost.

Authentication: an access token, sent as Authorization: Bearer <token>.

Name In Type Required Description
month query string or null no YYYY-MM; this month when left out
service_id query integer or null no Only this service's rows
meter query string or null no Only this meter's rows, for example memory_gib_hours
status query string or null no Only rows in this state: rated, charged, invoiced, blocked, waived
limit query integer or null no Rows to return. JSON answers 100 by default and at most 1000; a CSV answers up to 100000, the most it holds.
offset query integer no Rows to skip, newest hour first, to read the next page Default: 0.
format query string or null no csv for a CSV file; Accept: text/csv does the same
Status Meaning
200 JSON, or CSV when the request asks for it
422 The request is not valid. detail lists each problem.

Fields of a 200 response:

Field Type Description
month string
total integer How many rows match, before limit and offset
limit integer
offset integer
rows array of HourRowOut
rows[].id integer
rows[].hour string The start of the hour, in UTC
rows[].service_id integer
rows[].service string The deployment's name, or the server's host name
rows[].meter string
rows[].unit string
rows[].quantity string
rows[].included string
rows[].billable string
rows[].rate string The price of one unit when the hour was rated
rows[].amount string What the hour cost, four decimal places
rows[].currency string
rows[].status string rated, charged (paid from credit), invoiced, blocked or waived

A month of usage by service, meter and day

Section titled A month of usage by service, meter and day

GET /api/v1/billing/usage/summary

What the account's services used and cost in a month: each service with its meters (quantity, included, billable and cost), the same month by day, how much of the free amounts is used and where the month is heading.

groups, pools, forecast, forecast_basis and spend_limit read as they do in GET /billing/compute-usage. services lists every service billed by the second that has use in the month, the dearest first; a server that is switched off says so in stopped and costs its disk only. daily has one row for each day and meter, summed over the services, so a chart can draw cost or use by day. included_share is the use of the free amounts as one figure from 0 to 1, weighted by their rates; the server amounts count only with the Paid plan.

A free server, a service on a flat price and an organization's customer's service are never listed. This is the platform account's own usage: an organization's owner reads its customers' usage at /api/v1/orgs/{org_slug}/billing/usage-cost. Answers 422 for a month that is not YYYY-MM.

Authentication: an access token, sent as Authorization: Bearer <token>.

Name In Type Required Description
month query string or null no YYYY-MM; this month when left out
Status Meaning
200 Success.
422 The request is not valid. detail lists each problem.

Fields of a 200 response:

Field Type Description
month string YYYY-MM
currency string
through string or null The hour the figures are settled to, or null before any hour of the month is
forecast_basis string pace for this month, final for an earlier one and none in the first hours of a month
total string What the month cost so far
forecast string or null The month's cost if each running service keeps its pace; null when there is none to go on
included_share number or null How much of the free and included amounts you have used, from 0 to 1, each weighted by what it is worth at the rates. Null when no amount applies.
paid_plan Paid Plan active and the price of the Paid plan, which the server amounts need
groups array of object Each product group's meters and total, as GET /billing/compute-usage answers
pools array of object The free amounts of the web and server pools against use, as GET /billing/compute-usage answers
spend_limit object or null The account's budget with what counts against it, or null
services array of ServiceUseOut Each service with use this month, the dearest first
services[].service_id integer
services[].name string The deployment's name, or the server's host name
services[].group string app_deployment, cloud_compute or container_apps
services[].group_label string
services[].status string The service's status, for example active
services[].deployment_uuid string or null The deployment's uuid, for a service that has one; null for an instance
services[].stopped boolean True for a server that is switched off: it costs its disk only
services[].total string What the service cost this month so far
services[].meters array of MeterUseOut
daily array of DayOut Use and cost of each meter by day, oldest first, summed over the services
daily[].day string YYYY-MM-DD, in UTC
daily[].meter string
daily[].unit string
daily[].quantity string
daily[].cost string