Skip to main content

API overview

Base URL and versioning​

Backward compatibility is guaranteed for /v1/....

/api/... is used by the web client. It may change at any time; do not build integrations against it.

Authentication​

Keys (key_id and secret) are issued per application in the developer console.

Every /v1 request must be signed. All four headers are required:

X-Api-Key: ak_xxxxxxxxxxxx
X-Timestamp: <Unix seconds>
X-Nonce: <single-use random string>
X-Signature: <signature>

The signature is an HMAC-SHA256, keyed with your secret, over: method, path, canonicalised query, timestamp, nonce, and the SHA-256 of the request body. An expired timestamp or a repeated nonce is rejected — this is what stops an intercepted request from being replayed.

caution

/v1 does not accept Authorization: Bearer; sending one returns 401. If you need simple single-token authentication, use the MCP endpoint.

Scopes belong to the application, not the key. A key is a credential that can be rotated; permissions are an application property. Rotating a key does not change its permissions.

Idempotency​

Endpoints that spend balance, such as provisioning and renewal, require an Idempotency-Key header: 8–100 characters from [A-Za-z0-9-_.:].

Use the same key when retrying. The server returns the result of the first request instead of charging again.

Quotas​

Every response includes usage information:

X-RateLimit-Limit: 600
X-RateLimit-Remaining: 594
X-RateLimit-Reset: 1756512060
Automation dispatch uses a different quota unit

Dispatch is counted by device executions, not requests. A single request can dispatch to up to 200 devices; counting requests would underestimate the workload by a factor of 200. When the quota is exceeded, the response's unit field identifies the unit being counted.

Device identifiers​

Public requests always use our device_id (an integer). Upstream device identifiers are not returned.

If a request includes a device_id that does not belong to you, the entire request returns 404. The response does not identify which device caused the error; otherwise, the endpoint could be used to enumerate other users' devices.