Skip to main content
If you run querying.ai inside your own product, create one sub-account per customer. A sub-account has its own API keys, limits, tasks, batches and monitors. Its credits come from your balance, and the usage endpoints tell you what to charge each customer.

How a sub-account works

  • Its own keys and results. A sub-account key submits and reads tasks, batches and monitors like any other key, and sees only its own work. A task created with Acme’s key returns 404 to Globex’s key and to your own keys.
  • Your credits. Its tasks are charged to your balance. A sub-account has no balance, so its keys get 403 SUB_ACCOUNT_FORBIDDEN from GET /v1/credits and GET /v1/usage.
  • Your capacity. Your plan’s or contract’s concurrency limit covers your own tasks and every sub-account’s together, so sub-accounts never add capacity. GET /v1/async/status counts that shared queue for you, and a sub-account’s key gets 403 SUB_ACCOUNT_FORBIDDEN from it.
  • Your monitor limits. The monitors limit in GET /v1/monitors/capabilities counts your monitors and every sub-account’s together, and the prompts and tasksPerRun limits apply to a sub-account’s monitors as they do to yours.
  • Its own limits. monthlyCreditLimit caps what it can be charged in a UTC calendar month. concurrencyLimit caps its queued and running tasks inside your limit. Both are optional.
  • One level. A sub-account cannot have sub-accounts. Alert emails for its monitors go to your account’s admins.

Who can manage sub-accounts

Call the /v1/sub-accounts endpoints with one of your own API keys that has no engine scope and no daily credit limit. Any other key gets 403 SUB_ACCOUNT_FORBIDDEN, because a restricted key could otherwise issue keys without its own restrictions. A sub-account’s own keys get the same error.

Create a sub-account and a key

The response is 201:
Any other field returns 400 VALIDATION_ERROR, so a misspelled limit never leaves a customer uncapped. Then issue the sub-account a key:
key appears in this response only. Store it now; it is never shown again.
A key takes the same optional settings as a dashboard key: name (1–64 characters, default default), allowedTaskTypes, dailyCreditLimit and expiresAt (5 minutes to 2 years ahead). Send no body for a key with no restrictions. A sub-account can hold up to 5 active keys; revoked and expired keys do not count. A sixth returns 409 KEY_LIMIT. Revoke one first. Your customer’s key works on every endpoint like any other key:

Manage keys

GET /v1/sub-accounts/{id}/keys lists every key the sub-account has had, newest first, including revoked and expired ones. Check revokedAt and expiresAt to find the active keys.
DELETE /v1/sub-accounts/{id}/keys/{keyId} revokes a key and returns {"success": true, "data": {"revoked": "<keyId>"}}. A key that is already revoked, or not the sub-account’s, returns 404 NOT_FOUND.

Limits

Only the sub-account that reached its own limit is refused; your other customers keep running. A raised limit applies to the next request.
retryAfterSec counts to the start of the next UTC month, when the monthly count starts over. See Credits and limits for the account-wide limits.

Check a sub-account now

GET /v1/sub-accounts/{id} returns the sub-account with this month’s usage and activeTasks, the number of its tasks queued or running right now. Compare it with concurrencyLimit to see how close the customer is to its cap.
The values above are an example. In usage, credits and tasks are what was charged this UTC month, and reservedCredits is held by tasks still running.

Usage and billing

Every charge also appears on your own billing ledger; these endpoints split it by customer. Failed tasks are never charged and never count. Credit amounts carry up to two decimals.
  • GET /v1/sub-accounts lists your sub-accounts, oldest first, each with this month’s usage. Page with limit (default 100, at most 1,000) and pass nextCursor back as cursor.
  • GET /v1/sub-accounts/usage totals each sub-account over a range of UTC dates.
  • GET /v1/sub-accounts/{id}/usage gives one sub-account’s charges per day and engine.
Both usage endpoints take from and to as YYYY-MM-DD, inclusive. from defaults to the first of the current UTC month and to to today; a range spans at most 366 days.

All sub-accounts

For example:
Sub-accounts are listed largest first. A sub-account with no charge in the range is left out.

One sub-account

For example:
  • credits and tasks at the top are the totals of days.
  • days has one row per UTC date and engine that had a charge, ordered by date, then taskType. Days without charges have no row.
  • taskType: "OTHER" is a charge that is not a task, such as a monitor’s competitor read. It adds credits but no tasks.

Suspend and resume

  • Its keys return 401 within five seconds.
  • Its monitors stop running, and batch items that have not started end as API_KEY_INACTIVE.
  • Tasks already queued or running finish and are charged.
{"status": "active"} restores its keys and monitors. Each monitor runs once when it comes back rather than catching up on missed runs. The same PATCH changes name, externalId, monthlyCreditLimit and concurrencyLimit; null removes a limit or the externalId. A sub-account cannot be deleted; suspend it instead.

Errors

Endpoints