Replica Cache API
Replica Cache is a read-only REST API that serves NetBox data from an operationally independent cache, delivering sub-50ms P95 query latency and resilience independent of the primary NetBox database. It is available as a premium-tier feature on NetBox Cloud.
Customer Preview: Replica Cache is in customer preview. The API surface may evolve in future releases.
For the interactive API reference (OpenAPI/ReDoc), visit /docs on your Replica Cache endpoint.
Why Use Replica Cache
- Operational resilience - Replica Cache serves reads from an operationally independent cache. Your monitoring, reporting, and automation scripts keep working even during NetBox maintenance windows or outages.
- Fast reads at scale - Queries return in single-digit milliseconds for most workloads. Aggregation and filtering happen server-side, reducing data transfer and client-side processing.
- Zero load on the primary database - Every Replica Cache read is served from the cache. High-frequency polling, dashboards, and bulk data exports never touch the primary NetBox database.
Replica Cache complements the primary NetBox API - use it for read-heavy automation that benefits from speed and resilience, and continue using the primary API for writes and real-time consistency.
Replica Cache vs. TurboBulk: Both are premium-tier performance features. TurboBulk provides fast bulk reads and writes with exact consistency, operating directly against the primary database. Replica Cache offloads reads to an independent cache - eventually consistent, but zero primary database load and resilient to outages. They're complementary: TurboBulk for bulk writes and consistent reads, Replica Cache for high-frequency read automation and resilience.
Key Differences from the NetBox API
| Aspect | NetBox API | Replica Cache API |
|---|---|---|
| Base path | /api/ | /replica-cache/v1/ |
| Write support | Full CRUD | Read-only (GET) |
| Response format | Nested objects (e.g. nested site on device) | Flat rows (foreign keys are IDs) |
| Pagination | Offset-based (limit/offset) | Cursor-based (limit/cursor) |
| Filter syntax | ?name=foo | ?filter[name]=foo |
| Branching | Supports branches | Main branch only |
| Consistency | Real-time | Eventually consistent (typically <10s lag) |
| Authentication | Authorization: Bearer <key> | Authorization: Bearer <key> + NBC-Netbox-ID header |
Replica Cache is not a drop-in replacement for the NetBox API. Responses use flat column values rather than nested objects, filter syntax differs, and write operations are not supported.
Authentication
Every request to /v1/* endpoints requires two headers:
| Header | Value | Description |
|---|---|---|
Authorization | Bearer <api-key> | Your NetBox Cloud API token |
NBC-Netbox-ID | <tenant-id> | Your NetBox Cloud tenant ID, found in the Cloud console |
BASE_URL="https://<your-netbox>.cloud.netboxapp.com/replica-cache"
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/_meta/tables"
Use your existing NetBox Cloud API token - no separate credential is needed. Find your tenant ID in the NetBox Cloud console.
Quick Start
1. Discover available entities
Entity coverage varies by NetBox version and configuration. Start by listing the tables available in your cache:
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/_meta/tables"
{
"tables": [
{ "name": "dcim_device", "row_count": 1042 },
{ "name": "dcim_site", "row_count": 35 },
{ "name": "ipam_ipaddress", "row_count": 8491 }
]
}
2. List records
Query any entity using its {app}/{model} path (derived from the table name - dcim_device becomes dcim/devices):
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/dcim/devices?limit=2"
{
"count": 1042,
"next_cursor": "WzEsMl0",
"results": [
{ "id": 1, "name": "spine-01", "status": "active", "site_id": 5 },
{ "id": 2, "name": "spine-02", "status": "active", "site_id": 5 }
]
}
3. Get a single record
Fetch one record by its primary key:
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/dcim/devices/1"
{ "id": 1, "name": "spine-01", "status": "active", "site_id": 5 }
Querying
Filtering
Filter results using query parameters in the form filter[column]__operator=value. When no operator is specified, eq (exact match) is used.
# Devices with status "active" at site 5
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/dcim/devices?filter[status]=active&filter[site_id]=5"
Operators:
| Operator | Syntax | Description | Example |
|---|---|---|---|
eq | filter[col]=val or filter[col]__eq=val | Exact match (default) | filter[status]=active |
in | filter[col]__in=a,b,c | Match any value in comma-separated list | filter[status]__in=active,staged |
ilike | filter[col]__ilike=val | Case-insensitive substring match | filter[name]__ilike=spine |
isnull | filter[col]__isnull=true | Check for NULL (true) or NOT NULL (false) | filter[serial]__isnull=false |
gt | filter[col]__gt=val | Greater than | filter[id]__gt=100 |
lt | filter[col]__lt=val | Less than | filter[id]__lt=500 |
Column names correspond to database columns. Use the schema endpoint to discover available columns for each entity.
Sorting
Sort results with the sort parameter. Prefix with - for descending order:
?sort=name # ascending by name
?sort=-id # descending by id
Default sort order is ascending by primary key.
Field Selection
Return only specific columns with the fields parameter:
?fields=id,name,status
The primary key column is always included in the response, even if not listed.
Pagination
Replica Cache uses cursor-based pagination. Each list response includes:
| Field | Description |
|---|---|
count | Total number of rows matching your filters |
next_cursor | Opaque cursor string for the next page; null on the last page |
results | Array of records for the current page |
Use the limit parameter to control page size (default: 50, maximum: 1000).
To paginate through all results, pass the next_cursor value from each response as the cursor parameter on the next request:
cursor=""
while true; do
response=$(curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/dcim/devices?limit=100${cursor:+&cursor=$cursor}")
# Process results...
echo "$response" | jq '.results[]'
# Get next cursor; exit loop if null (last page)
cursor=$(echo "$response" | jq -r '.next_cursor // empty')
[ -z "$cursor" ] && break
done
Aggregation
Compute aggregate metrics without fetching individual records:
GET /v1/{app}/{model}/_aggregate
Parameters:
| Parameter | Description |
|---|---|
metric | count (default), sum, avg, min, or max |
metric_field | Column to aggregate (required for all metrics except count) |
group_by | Comma-separated columns to group by (maximum 3) |
Example - count devices by status:
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/dcim/devices/_aggregate?metric=count&group_by=status"
{
"results": [
{ "status": "active", "value": 892 },
{ "status": "planned", "value": 120 },
{ "status": "offline", "value": 30 }
]
}
Example - average prefix length by VRF:
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/ipam/prefixes/_aggregate?metric=avg&metric_field=prefix_length&group_by=vrf_id"
Search
Search across cached entities with a substring match:
GET /v1/_search?q=<term>
q- search term (minimum 2 characters)limit- maximum results to return (default: 50, maximum: 200)
Results are drawn from NetBox's cached value index, matching across object representations.
Data Freshness
Check how recently each table was synchronized from the primary database:
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/_meta/freshness"
{
"tables": {
"dcim_device": {
"last_flush": "2025-01-15T12:34:56Z",
"lag_ms": 3200
},
"dcim_site": {
"last_flush": "2025-01-15T12:34:55Z",
"lag_ms": 4100
}
}
}
| Field | Description |
|---|---|
last_flush | UTC timestamp of the most recent sync for this table |
lag_ms | Milliseconds elapsed since last_flush (wall-clock lag at query time) |
Under normal operation, lag_ms is typically under 10 seconds. Use this endpoint to verify freshness in automation pipelines or monitoring.
Schema Discovery
Replica Cache schema depends on your NetBox version and installed plugins. Use the metadata endpoints to discover available tables and columns at runtime.
List tables and row counts:
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/_meta/tables"
{
"tables": [
{ "name": "dcim_device", "row_count": 1042 },
{ "name": "dcim_site", "row_count": 35 }
]
}
Get column schema for a table:
curl -s \
-H "Authorization: Bearer $API_KEY" \
-H "NBC-Netbox-ID: $TENANT_ID" \
"$BASE_URL/v1/_meta/tables/dcim_device/schema"
{
"table": "dcim_device",
"columns": [
{ "name": "id", "type": "BIGINT", "nullable": "NO" },
{ "name": "name", "type": "VARCHAR", "nullable": "YES" },
{ "name": "status", "type": "VARCHAR", "nullable": "NO" },
{ "name": "site_id", "type": "BIGINT", "nullable": "YES" }
]
}
Build filters and field selections against the columns returned here rather than hardcoding column names.
Error Handling
Errors are returned as JSON with an error field:
{ "error": "missing tenant header" }
Status codes:
| Code | Meaning |
|---|---|
200 | Success |
400 | Bad request - invalid filter, cursor, sort column, or missing parameter |
401 | Unauthorized - missing or invalid API key |
404 | Not found - unknown endpoint, table, or record |
405 | Method not allowed - only GET requests are supported |
500 | Internal server error - query execution failed |
Limitations
- Read-only - no create, update, or delete operations. Use the primary NetBox API for writes.
- Eventually consistent - data reflects the primary database with a short delay (typically <10s). Do not rely on Replica Cache for read-after-write consistency.
- Main branch only - Replica Cache serves data from the main NetBox branch. Branching plugin branches are not available.
- Flat responses - related objects are represented by foreign key IDs, not nested objects. Join data client-side if needed.
- Schema varies by NetBox version - available columns may change across NetBox upgrades. Use the schema endpoint to discover columns at runtime.
- Non-core object types require configuration - core NetBox object types are available by default. Plugin models and non-core types can be enabled by contacting the NetBox Cloud support team.
- Customer preview - the API surface may change in future releases.
API Reference
All endpoints below require the Authorization and NBC-Netbox-ID headers.
| Endpoint | Description | Key Parameters |
|---|---|---|
GET /v1/_meta/tables | List available tables and row counts | - |
GET /v1/_meta/tables/{table}/schema | Get column definitions for a table | - |
GET /v1/_meta/freshness | Per-table sync freshness | - |
GET /v1/_search | Cross-entity substring search | q, limit |
GET /v1/\{app\}/{model} | List records | filter[col]__op, sort, fields, limit, cursor |
GET /v1/\{app\}/\{model\}/{id} | Get a single record by primary key | - |
GET /v1/\{app\}/{model}/_aggregate | Aggregate metrics | metric, metric_field, group_by |
For the full OpenAPI specification, visit /docs on your Replica Cache endpoint.