API Reference
The Voxel API gives you programmatic access to everything in your workspace — items, collections, ingestion jobs, and usage data — through a predictable REST interface.
Every endpoint speaks JSON, uses standard HTTP verbs and status codes, and returns cursor-based pages. Test freely against the sandbox: nothing you do there touches production data.
Base URL
All requests are made over HTTPS to the URL below. Plain-HTTP requests are rejected, and the current stable version is pinned in the path — breaking changes only ever ship in a new version.
https://api.voxel.dev/v1
Authentication
Authenticate every call with a secret API key sent in the Authorization header. Create and rotate keys in the dashboard — each key is scoped to a single environment (sandbox or production).
Authorization: Bearer YOUR_API_KEY
Keys carry full workspace access — keep them server-side, out of client code and version control, and rotate immediately if one leaks.
Making requests
List the items in your workspace with a single authenticated GET. Responses are JSON; send Accept: application/json and you will always get a machine-readable body — even for errors.
curl -X GET "https://api.voxel.dev/v1/items?limit=25" \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Accept: application/json"
import requests
resp = requests.get(
"https://api.voxel.dev/v1/items",
headers={
"Authorization": "Bearer YOUR_API_KEY",
"Accept": "application/json",
},
params={"limit": 25},
)
resp.raise_for_status()
items = resp.json()["items"]
const resp = await fetch("https://api.voxel.dev/v1/items?limit=25", {
headers: {
Authorization: "Bearer YOUR_API_KEY",
Accept: "application/json",
},
});
if (!resp.ok) throw new Error(`Request failed: ${resp.status}`);
const { items, next_cursor } = await resp.json();
Endpoint overview
The endpoints you will reach for most. Every one accepts and returns JSON, and list endpoints share the same cursor-pagination contract.
| Method | Endpoint | Description |
|---|---|---|
| GET | /v1/items | List items in your workspace, newest first. |
| GET | /v1/items/{id} | Retrieve a single item by its unique ID. |
| POST | /v1/items | Create a new item from a JSON payload. |
| GET | /v1/collections | List collections along with item counts and metadata. |
| POST | /v1/ingest | Ingest up to 1,000 records in a single batched call. |
Endpoint details
A closer look at the workhorse of the API. Combine limit with the returned next_cursor to page through results of any size.
Query parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| limit | integer | No | Results per page. Defaults to 25, max 100. |
| offset | integer | No | Records to skip before the first result. |
| filter | string | No | Filter expression, e.g. status:active. |
| sort | string | No | Sort key with direction, e.g. -created_at. |
Path parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| id | string | Yes | Unique item identifier, used by the /{id} variant. |
Error responses
| Status | Code | Description |
|---|---|---|
| 400 | invalid_request | Malformed query parameter or body. |
| 401 | unauthorized | Missing or invalid API key. |
| 404 | not_found | The requested item does not exist. |
| 429 | rate_limited | Too many requests — retry after the reset time. |
Response
{
"items": [
{
"id": "itm_9f3KZq7L",
"name": "Quarterly usage export",
"status": "active",
"created_at": "2026-07-14T09:12:33Z"
}
],
"has_more": true,
"next_cursor": "cur_aH52xW"
}
Guides & resources
Short, practical reads that take you from first request to production-grade integration.
Authentication guide
Create keys, scope them per environment, and rotate secrets safely.
Read guide
Pagination best practices
Use cursors to walk large result sets reliably — no skipped rows.
Read guide
Webhooks overview
Receive real-time events with signed, retried deliveries.
Read guide
SDKs & libraries
Official clients for TypeScript, Python, Go, and Ruby.
View SDKsRate limits
Limits apply per API key over a rolling one-minute window. Every response includes headers you can use to pace clients and back off cleanly.
Standard plan
1,000 requests / minute
Bursts up to 2,000 req/min are absorbed automatically. Need more headroom? Talk to sales.
Response headers
X-RateLimit-LimitMaximum requests allowed in the current window.X-RateLimit-RemainingRequests you have left before throttling kicks in.X-RateLimit-ResetUnix timestamp when the window resets.