API readiness
GET /livez is process-only liveness; upstream or database failure must not cause a restart loop.
GET /api/v1/stats/health returns HTTP 200 only when MySQL is reachable and every expected configured chain/contract has successful required discovery less than five minutes old. Empty/missing sync rows, partial configuration and stale or absent discovery return HTTP 503. Successful quiet scans count; new bridge transfers are not required for health. Old rows outside the configured set are ignored.
The expected set follows the known-chain environment loader, retaining incomplete RPC/locker configurations and existing explicit-enable gates. Any configured EVM bridge requires its Casper side. An empty configured set is not ready. API and separately run indexer processes must use matching expected chain/contract configuration.
For full ingestion, provide the intended {NAME}_RPC_URL and {NAME}_LOCKER (or their existing CHAIN_ aliases), CASPER_TOKEN_FACTORY_HASH, CASPER_NODE_URL and a valid CSPR_CLOUD_ACCESS_KEY. Required RPC endpoints must use HTTP(S). Optional WSS is not a general readiness requirement; configured stream outages have independent monitoring.
Without Casper REST credentials, otherwise configured RPC recovery can continue, but the response is explicitly mode: recovery-only, status: degraded, HTTP 503 on both fresh and stale databases. It is not a new selectable deployment mode or a readiness bypass. Rejected credentials/upstream errors cannot refresh discovery; a previous success expires after five minutes.
Casper-only and no-chain ingestion are unsupported. Both combined and standalone indexer startup reject configurations without a valid EVM RPC/locker pair before opening listeners. A standalone API or RUN_INDEXERS=false may read a shared database, but Casper-only/empty configuration can never report full-ingestion readiness, even with fresh historical rows. An EVM-only configuration starts EVM ingestion but remains unready until the required Casper side is configured and successfully discovers events.
Both indexer entrypoints share one private metrics listener and release it on shutdown or startup failure. API-only combined mode releases its metrics listener too. Rejected static configurations need operator correction; upstream discovery failures affect readiness, not process liveness. See the repository startup support matrix for requirements and cleanup behavior.
checks.indexers remains a chain-to-boolean map. checks.ingestion exposes bounded per-chain configurationReady, discoveryConfigured, discoveryReady and lastDiscoverySuccess epoch seconds. Credentials and provider URLs are not exposed.
Apply migration 024_ingestion_health.sql through the normal migration job before the new image. Discovery evidence is distinct from cursor writes and recovery-loop timestamps and is not seeded from old sync rows. A fresh successful scan is required after upgrade. Readiness certifies recent required discovery, not full historical completeness or an empty recovery queue. Parked obligations remain unresolved even when oldest active recovery age is zero; they have a separate fifteen-minute operator-triage alert.
See the operator readiness contract and alert runbooks. The authoritative make-infra rules and their rendered tests must accompany the application. #546's baseline monitoring remains separately owned. Actual scrape, loaded-rule, receiver and notification delivery verification belongs to the separately approved #112 rollout—not local tests or PR approval. Preserve single-replica/Recreate operation.