hosting

GET /v1/sites/{siteId}/metrics

Get a site's current usage metrics.

All hosting endpoints

Authentication

Send an API key as a bearer token. This endpoint does not state a specific permission in the specification, so give your key the least it needs and check the response rather than assuming.

This endpoint takes no organisation id. Your key already identifies the organisation it belongs to, and the response is scoped to it.

Try it

Replace anything in angle brackets with your own values, and the key placeholder with a key from your dashboard.

curl -X GET https://api.zinndigital.com/v1/sites/{siteId}/metrics \
  -H "Authorization: Bearer zdk_live_…"

Signed in? The API console in your dashboard fills in your real organisation id and your own key, and runs the request against the live API so you can see the actual response. Open this endpoint in the API console

Details

Point-in-time usage for the Overview panel — disk, bandwidth, visits, the PHP version, the TLS state, and a short daily bandwidth series for the usage chart. RLS-scoped to a site the caller can view (`sites.view`); an out-of-scope or unknown id is a `404`, exactly like `getSite`. **Collection is asynchronous.** Metrics are gathered off the request path (a scheduled pull from the site's fleet worker into a cached store — never a live per-request driver call, CLAUDE.md §2.16) and read back here. Until a sample has been collected — a freshly-provisioned or suspended site, or a site on a worker not yet reporting — `available` is `false`, `collected_at` is `null` and the usage counters are `null`; the shape is stable so the client renders "usage not yet available" without a contract change once the collector populates it.

Parameters

NameTypeRequiredWhat it is
siteId (path)UuidYesSite ID (UUIDv7).

Response

NameTypeRequiredWhat it is
availablebooleanYesWhether a metrics sample has been collected for this site yet.
disk_used_mbobjectYesDisk the site is using, in MB, from the newest stored hourly reading. `null` when nothing has measured it yet **or** when the newest reading is too old to present as current — t…
disk_limit_mbobjectYesThe disk ceiling ENFORCED on the box, in MB, as last stored. `null` when no ceiling is recorded. ⛔ Not the plan allowance — see `getSiteQuota`, which returns both separately bec…
bandwidth_mbobjectYesBandwidth used in the current period.
visitsobjectYes
php_versionstringNoThe PHP version the site runs; empty when not applicable/unknown.
serving_okobjectNoWhether the site actually answered over HTTPS **from outside the box** at `serving_checked_at`, established by the recurring serving sweep rather than on this request. `null` me…
serving_checked_atobjectNoWhen a DEFINITE serving verdict was last obtained; `null` until one has been. Deliberately separate from the sweep's rotation cursor, which advances for every site the sweep rea…
serving_detailstringNoThe short status line behind `serving_ok` — `"HTTP 522"`, `"ConnectTimeout"`. Never a raw vendor response body.
ssl_statusstring<active, pending, none, unknown>NoThe site's TLS certificate state.
ssl_expires_atobjectNo
bandwidth_seriesinteger[]YesRecent daily bandwidth samples (MB), oldest first — for the usage chart. Empty when unavailable.
collected_atobjectYesWhen this sample was collected; null when unavailable.
error_rateSiteErrorRateYesHTTP and PHP errors for one site over the newest closed collection window (#626). What `features/uptime-monitoring` sells: *"HTTP and PHP errors captured per site, so a fatal fr…

Errors this endpoint can return

401 · 403 · 404 · 429