---
title: "Get the current account's billing standing"
method: GET
path: "/v1/users/me/billing"
tags: ["Users"]
---

# Get the current account's billing standing

`GET /v1/users/me/billing`

## Request

- Base URL: `https://api.naturali.ai`
- URL: `https://api.naturali.ai/v1/users/me/billing`
- Auth: one of:
  - HTTP bearer
  - OAuth 2 (authorization code, authorization URL `https://api.naturali.ai/authorize`, token URL `https://api.naturali.ai/token`, scopes: `mcp:access`)

The plan the account is on, how long its projects may keep content, how much indexed storage it is holding, and the credit it has left — the figures the platform already enforces against, readable by the account they are enforced against.

A managed-model generation is refused with `402 insufficient_credit` while `credit_balance_usd` is negative, and a feature or a resource count outside the plan is refused with `403`, as is a retention window wider than `retention_days` or an ingest past `storage.limit`. Every refusal names what is missing; this is where the numbers behind them are read.

Every figure here is a local read, which is what keeps this route cheap enough to poll — unlike `GET /v1/users/me/usage`, which asks the meter once per project.

Answers for the caller's own account only, and always the account the credential resolves to — an API key answers for the user that minted it. The plan gating a *project* is that project's billing owner's, so a member of someone else's project reads their own rung here, not that project's.

## Response `200`

The account's plan and credit standing.

- UserBilling
  - `plan` 'free' | 'pro' | 'business' | 'enterprise', required: The rung of the infra subscription in effect for this account: the highest it held this month. `free` for an account with no subscription, which is also the least-privileged rung. It gates the feature lines and the resource counts of the pricing table.
  - `next_plan` 'free' | 'pro' | 'business' | 'enterprise', required: The rung the account moves to when the month turns. It differs from `plan` only while a downgrade is pending: a downgrade takes effect at the end of the month, an upgrade at once.
  - `retention_days` integer, nullable, required: The longest window a project of this account may keep trace and generation content for, in days. A `PATCH` asking for a wider one — `null` included, which keeps content indefinitely — is refused with `403 plan_limit_reached`; anything shorter is always allowed. On a plan whose window a contract sets, this is that contract's figure, and `null` means nothing bounds it. A plan change that shortens the window applies at the end of the billing cycle, so this reads as the widest window held during the current one.
  - `credit_balance_usd` number, required: Model credit left, in US dollars — granted and purchased credit plus the plan's monthly allowance, less managed-model and embedding spend. Managed generations and writes that embed are refused while this is negative; zero is not. Only as current as `spend_reconciled_at`, so read the two together.
  - `earned_balance_usd` number, required: Marketplace earnings: the publisher's share of fees its consumers funded, less withdrawals. Never lapses.
  - `paid_balance_usd` number, required: What may fund a marketplace fee: purchased credit plus earnings, less the usage included and granted credit did not cover and the fees paid. Included and granted credit never fund a fee, so a call to a priced installed tool or agent is refused with `402 insufficient_credit` while this is not positive.
  - `spend_reconciled_at` string, date-time, nullable, required: When spend was last read off the meter and written to the ledger. `null` when it has never been read for at least one of the account's projects, or the account has none — a balance whose spend has never been read is not current as of anything.
  - `storage` object, required: The account's indexed-storage pool, in the metered gigabytes the ceiling is enforced in — the raw file plus every chunk's text and its embedding vector, so not the size of what you uploaded. Pooled across every project the account pays for; per project, read the `gb_day` component of `GET /v1/projects/{project_id}/usage`. An ingest past `limit` is refused with `403 plan_limit_reached`, `resource: "storage"`, whose `details` carry the same `limit` and `used`.
    - `used` number, required: GB held across the account's projects.
    - `limit` number, nullable, required: GB the plan allows; null where a contract sets the ceiling, or where the plan sets none.
    - `sampled_at` string, date-time, nullable, required: When the **oldest** sample behind `used` was taken — the total is only as current as its stalest part, measured every few minutes per project rather than on this request. Null when a project has never been sampled, or there are none.

## Other responses

- `401`: Missing or invalid credentials.

---

[API](https://skmtc.dev/naturali/apis/naturali-ai-api.md) · [All operations](https://skmtc.dev/naturali/apis/naturali-ai-api/llms.txt) · [OpenAPI document](https://skmtc.dev/naturali/apis/naturali-ai-api/revisions/e4905b78f422?raw)
