Skip to content

Health & IBD

Server Health and Initial Block Download Reference

blockd exposes server health through two interfaces:

WebSocket — subscribe to server.health for real-time push events at a configurable interval. This is the preferred method for applications that need continuous health monitoring without polling. See Health Events.

REST — poll GET /health on demand. Available before blockd reaches ready state, making it suitable for readiness probes and one-off checks. See REST Version & Health.

Both interfaces return the same data. This page is the complete field reference for both.


Base fields (always present):

{
"time": 1771612931,
"up_since": 1771612819,
"state": "ready",
"ready_at": 1771612824,
"tracking_since": 1771612824
}

With tip:

{
"tip": {
"time": 1771612349,
"height": 292411,
"hash": "00000000590f69588b42f409796be4049ad8c4528e04f26f2fdabebbab7e0e18"
}
}

With detailed:

{
"core": {
"state": "synced",
"connected_at": 1771612823,
"polled_at": 1771613117,
"rpc_errors": 0,
"zmq_outages": 0
},
"indexer": {
"state": "synced",
"connected_at": 1771612823,
"polled_at": 1771613064,
"disconnects": 0,
"degradations": 0,
"errors": 0,
"tracking_since": 1771612824
}
}

core fields:

FieldDescription
stateSee bitcoind states above
connected_atUnix timestamp when blockd connected to bitcoind
polled_atUnix timestamp of the most recent RPC poll
rpc_errorsRPC error count since blockd started
zmq_outagesSee ZMQ monitoring below
zmq_outage_atSee ZMQ monitoring below

indexer fields:

FieldDescription
stateSee indexer states above
connected_atUnix timestamp when blockd connected to the indexer
polled_atUnix timestamp of the most recent indexer poll
disconnectsDisconnection count since blockd started
degradationsDegradation event count since blockd started
errorsError count since blockd started
tracking_sinceSee Cache invalidation below

tracking_since is mirrored as a top-level base field for convenience — callers that only need this value don’t have to request the detailed level. Both fields always carry the same value.

During IBD, ibd is present:

{
"ibd": {
"blocks_synced": 450000,
"blocks_total": 892411,
"per_sec_5min": 142.3,
"per_sec_total": 98.7,
"est_progress": 0.5039
}
}

All timestamps are Unix seconds.

Optional fields:

FieldPresent when
ready_atServer has reached ready state
tracking_sinceIndexer is synced with bitcoind — see Cache invalidation
tipRequested via REST level or WebSocket subscription arg
ibdbitcoind is in initial block download
coreRequested via REST detailed level or WebSocket subscription arg
indexerRequested via REST detailed level or WebSocket subscription arg

Server state:

StateDescription
offlinebitcoind or Fulcrum is unreachable
ibdbitcoind is in initial block download
syncingbitcoind is syncing after IBD
readyAll services synced and ready to serve requests
degradedOne or more services are experiencing errors

bitcoind state (core.state):

StateDescription
offlinebitcoind is unreachable
ibdInitial block download in progress
syncingCatching up to chain tip
syncedAt chain tip and healthy
degradedReachable but experiencing RPC or ZMQ errors

Indexer state (indexer.state):

StateDescription
disconnectedFulcrum is unreachable
connectedConnected but not yet synced
syncingBuilding or catching up its index
syncedAt chain tip and healthy
degradedConnected but experiencing errors

message:

FieldTypePresent when
core.messagestringA fault or warning condition exists on bitcoind
indexer.messagestringA fault or warning condition exists on the indexer

Omitted entirely under normal operating conditions. When present, suitable for display in application UIs.

Example core messages:

"RPC error: down"
"catching up - 12 blocks remaining"
"no peer connections"
"slow - no block for 56 minutes but healthy. mempool: 1034 peers: 21"
"warning - no block for 45 minutes. mempool: 1231 peers: 16"
"critical - no block for 65 minutes. mempool: 0 peers: 0"

Example indexer messages:

"indexer is more than one block behind"

If tracking_since changes from a previously observed value, all cached workflow results are stale — re-submit workflows and re-fetch transactions and UTXOs for all tracked pubkeys sets.


blockd monitors all ZMQ connections to bitcoind using socket-level monitoring. Most Bitcoin node integrations do not monitor ZMQ at this depth — blockd exposes this information so applications can make informed decisions about node stability.

FieldDescription
zmq_outagesNumber of ZMQ disruptions since blockd started
zmq_outage_atUnix timestamp of the most recent ZMQ outage. Absent if none have occurred

A value of 0 for zmq_outages means a ZMQ connection has been stable throughout. Values greater than 0 indicate disruptions occurred — ZMQ reconnects automatically, but non-zero counts suggest the node may have experienced instability. ZMQ outages do not affect the server state field, which may still read ready during or after a disruption.


Present only when state is ibd. Absent entirely during normal operation.

FieldTypeDescription
blocks_syncedintegerCurrent block height received
blocks_totalintegerTotal blocks expected (chain tip height)
per_sec_5minfloatBlocks per second over the most recent 5 minutes. Absent until enough data has been gathered
per_sec_totalfloatBlocks per second over the entire IBD. Absent until enough data has been gathered
est_progressfloatEstimated sync progress — see below
messagestringPresent only when a stall condition is detected — see below

A float sourced from bitcoind’s getblockchaininfo verificationprogress field, rounded by blockd.

bitcoind estimates sync progress as the ratio of transactions processed so far to a projected total transaction count. The projected total is calculated from a hardcoded checkpoint (transaction count + timestamp, updated each Bitcoin Core release) extrapolated forward using an assumed transaction rate. This gives a more meaningful picture of sync progress than block height alone, since early blocks contain very few transactions.

The value will typically reach 0.9999 or above when the node is nearly or fully synced, and may slightly exceed 1.0 if the actual transaction rate has outpaced the estimate baked into the running Bitcoin Core version.

Regtest: est_progress is always reported as 1 on regtest networks, as no transaction rate statistics are defined for that network type.

Present only when a stall condition is detected. Suitable for display in application UIs.

MessageCondition
"stalled - network disabled"Network connectivity is disabled
"stalled - no peers"No peer connections
"stalled - 0 peers connected"Peer count is zero
"stalled - validation backlog 112 blocks behind"Validation more than 100 blocks behind
"stalled - slow validation 5 blocks behind"Validation more than 10 blocks behind
"stalled - unknown"Stall detected but cause cannot be diagnosed

The block count in validation backlog and slow validation messages reflects the current lag at the time of the event.