Health omits coverage and pagination fields
Health is the source of truth for adapter status, so its _meta includes only request_id and response_generated_at. It omits _meta.sources, _meta.query_coverage, and _meta.pagination entirely.
Developers
Health
Overview
/v1/health
Health is the adapter-status source of truth. Use it to inspect adapter freshness, live aggregation eligibility, and infrastructure health without inferring those states from data endpoints.
Path and query parameters are documented together so the request surface stays easy to scan.
Use the same endpoint across all three snippets. The tabs switch only the client syntax.
cURL
curl -sS "https://api-staging.mountainswitch.co/v1/health" \
-H "Accept: application/json" TypeScript
const response = await fetch(
"https://api-staging.mountainswitch.co/v1/health",
{
headers: {
Accept: "application/json",
},
},
);
const payload = await response.json(); Python
import requests
response = requests.get(
"https://api-staging.mountainswitch.co/v1/health",
headers={"Accept": "application/json"},
)
payload = response.json()
The example response shows the documented JSON envelope with endpoint data in
data and request metadata in
_meta.
{
"data": {
"overall": "degraded",
"adapters": [
{
"adapter_id": "ca-chain-controls",
"jurisdiction": "US-CA",
"feed_type": "chain-controls",
"status": "healthy",
"live_aggregation_eligible": true,
"last_successful_fetch": "2026-03-19T12:47:00Z",
"last_attempted_fetch": "2026-03-19T12:47:00Z",
"consecutive_failures": 0,
"last_error": null,
"record_count": 45,
"average_latency_ms": 340
},
{
"adapter_id": "ca-lane-closures",
"jurisdiction": "US-CA",
"feed_type": "lane-closures",
"status": "stale",
"live_aggregation_eligible": false,
"last_successful_fetch": "2026-03-19T12:35:00Z",
"last_attempted_fetch": "2026-03-19T12:47:00Z",
"consecutive_failures": 2,
"last_error": "HTTP 503 from upstream",
"record_count": 120,
"average_latency_ms": 890
}
]
},
"_meta": {
"request_id": "req_health_docs",
"response_generated_at": "2026-03-19T19:47:30Z"
}
} This reference stays flat on purpose so the documented fields remain easy to scan.
These rows keep the repo-wide rate-limit and infrastructure behavior visible without inventing endpoint-specific transport semantics.
| Status | Code | When it happens |
|---|---|---|
| 429 | RATE_LIMIT_EXCEEDED | The caller exceeded the shared API rate limit. |
| 503 | SERVICE_UNAVAILABLE | D1 or another critical dependency is unavailable. |
These notes capture the contract edges that matter most for consumers of the endpoint.
Health is the source of truth for adapter status, so its _meta includes only request_id and response_generated_at. It omits _meta.sources, _meta.query_coverage, and _meta.pagination entirely.
Clients must not re-derive live aggregation eligibility from status or last_successful_fetch. The API computes live_aggregation_eligible at request time and uses that value directly for list and summary coverage decisions.
GET /v1/health and GET /v1/health/:adapterId are never written to response KV and must always return Cache-Control: no-store.
Subsection
/v1/health/:adapterId
Use the single-adapter health endpoint when the caller needs one adapter's effective status, live aggregation eligibility, and bootstrap or missing-health fallback behavior.
Path and query parameters are documented together so the request surface stays easy to scan.
adapterId
Path Requiredstring
Registered adapter identifier such as ca-chain-controls. Unknown identifiers return 404 ADAPTER_NOT_FOUND.
| Name | Location | Required | Type | Description |
|---|---|---|---|---|
| adapterId | Path | Yes | string | Registered adapter identifier such as ca-chain-controls. Unknown identifiers return 404 ADAPTER_NOT_FOUND. |
Use the same endpoint across all three snippets. The tabs switch only the client syntax.
cURL
curl -sS "https://api-staging.mountainswitch.co/v1/health/ca-chain-controls" \
-H "Accept: application/json" TypeScript
const response = await fetch(
"https://api-staging.mountainswitch.co/v1/health/ca-chain-controls",
{
headers: {
Accept: "application/json",
},
},
);
const payload = await response.json(); Python
import requests
response = requests.get(
"https://api-staging.mountainswitch.co/v1/health/ca-chain-controls",
headers={"Accept": "application/json"},
)
payload = response.json()
The example response shows the documented JSON envelope with endpoint data in
data and request metadata in
_meta.
{
"data": {
"adapter_id": "ca-chain-controls",
"jurisdiction": "US-CA",
"feed_type": "chain-controls",
"status": "healthy",
"live_aggregation_eligible": true,
"last_successful_fetch": "2026-03-19T12:47:00Z",
"last_attempted_fetch": "2026-03-19T12:47:00Z",
"consecutive_failures": 0,
"last_error": null,
"record_count": 45,
"average_latency_ms": 340
},
"_meta": {
"request_id": "req_health_adapter_docs",
"response_generated_at": "2026-03-19T19:47:30Z"
}
} This reference stays flat on purpose so the documented fields remain easy to scan.
These rows keep the repo-wide rate-limit and infrastructure behavior visible without inventing endpoint-specific transport semantics.
| Status | Code | When it happens |
|---|---|---|
| 404 | ADAPTER_NOT_FOUND | The requested adapterId is not present in the registered adapter registry. |
| 429 | RATE_LIMIT_EXCEEDED | The caller exceeded the shared API rate limit. |
| 503 | SERVICE_UNAVAILABLE | D1 or another critical dependency is unavailable. |
These notes capture the contract edges that matter most for consumers of the endpoint.
If health:{adapterId} is missing, the API distinguishes true bootstrap from post-boot missing health using lastCompletedCycle:{adapterId}. The response is synthesized but not written back to KV.
GET /v1/health/:adapterId returns the same public AdapterHealthApiSchema used inside GET /v1/health data.adapters[].
GET /v1/health/:adapterId is not part of the query_coverage cache matrix and must always return Cache-Control: no-store.