Skip to main content

Monitoring

How to check that a RushDB server is alive and ready, collect its metrics and logs, and what to alert on. Every metric is listed in the metrics reference.

Health and readiness​

EndpointAuthPurpose
GET /healthnoneLiveness: the process is running.
GET /readynoneReadiness: the node can serve and persist writes.
curl -s http://127.0.0.1:3000/health
# {"status":"ok","engine":"rushdb-lmpg","protocolVersion":1,"queryLanguages":["gremlin","mongo","searchQuery","sql","sqlPgq"]}
curl -s http://127.0.0.1:3000/ready
# {"status":"ready","commitIndex":182344,"dataDir":"/var/lib/rushdb"}

/ready returns 503 with a reason when:

reasonMeaningAction
boot phase (status: starting)Still opening storage or starting engines.Wait.
maintenance modeStarted with --maintenance.Expected during maintenance.
store is shutting downShutdown in progress.Expected during a stop.
durable publisher failedThe write path hit an unrecoverable error (for example the disk filled up). error has the detail.Fix the cause and restart.
data directory is not writableThe readiness probe file could not be written.Check permissions, mount, disk.
free disk below thresholdFree space below disk-space-threshold-percent. Writes get unavailable (HTTP 503).Free disk space.
vector indexes are still warmingOnly with --require-index-warmup.Wait.

Use /health for liveness probes (restarting a node that is busy recovering does not help) and /ready for load-balancer membership.

Warning: In maintenance mode /health also returns 503 ({"status":"maintenance"}). If your orchestrator restarts on a failed liveness probe, treat that body as alive, or disable the liveness probe while in maintenance.

Prometheus metrics​

GET /metrics needs the boot token or a capability with read permission:

# prometheus.yml
scrape_configs:
- job_name: rushdb
scrape_interval: 15s
metrics_path: /metrics
authorization:
type: Bearer
credentials_file: /etc/prometheus/rushdb-token
static_configs:
- targets: ['127.0.0.1:3000']

In multitenant mode, a capability used for scraping must be bound to a tenant and the scrape must send that tenant in X-RushDB-Tenant; the boot token needs no tenant header.

Scrapes are cheap: the expensive storage byte breakdown is computed in the background every 15 minutes and served from cache. Use --metrics-prefix to namespace the metrics and --metrics-filter to export a subset.

Key metrics​

AreaMetricWatch for
Trafficrate(rushdb_requests_total[5m]) by routeThroughput per operation.
Latencyhistogram_quantile(0.99, rate(rushdb_request_duration_seconds_bucket[5m]))Slow operations.
Commitsrushdb_commit_latency_seconds, rushdb_commit_phase_seconds{phase="wal_append_sync"}fsync latency of the disk.
Write ratederiv(rushdb_commits_total[5m])Commits per second.
Saturationrushdb_scheduler_inflight / rushdb_scheduler_capacityNear 1 means requests will be shed with 503.
Memoryrushdb_allocator_resident_bytes, rushdb_budget_used_bytes{pool="managed"} / rushdb_budget_limit_bytes{pool="managed"}Approaching the host or container limit; managed budget exhaustion.
Diskrushdb_storage_file_bytes, rushdb_wal_retained_bytesGrowth; WAL held by a lagging consumer.
Retentionrushdb_retention_consumers, rushdb_retention_protected_floor, rushdb_retention_oldest_reader_commitA consumer or reader pinning history.
Maintenancerushdb_gc_tick_seconds, rushdb_storage_compactions_totalMaintenance falling behind.
Searchrushdb_text_pending, rushdb_ann_exact_fallbacks_totalText index backlog; vector cache too small.
Tenantsrushdb_tenants_resident, rushdb_tenant_resident_bytesResidency budget pressure.

Logs​

The server logs to stderr (captured by journald under systemd). Control verbosity with RUST_LOG; the default is rushdb_server=info,tower_http=info.

MessageLevelMeaning
rushdb listeninginfoStartup complete, with the bound ports and tenancy.
slow protocol callwarnAn HTTP request took at least logs-query-threshold-ms (default 5 s). Fields: op, scope, elapsed_ms, rows, ok.
storage compaction completeinfoIdle compaction ran; before_bytes, after_bytes.
compaction deferredinfoCompaction could not run this time; retried next interval.
resident memory over watchdog limit; reclaimingwarnRSS above --rss-max.
WAL archiving failedwarnThe archiver could not write a segment.
WAL archive fell behind the retention caperrorThe archive now has a gap; take a new base backup.
WAL archive byte cap removed segments inside the retention windowwarnThe PITR window shrank.
durability checkpoint failedwarnA periodic checkpoint failed.
incremental GC tick failedwarnA maintenance tick failed.
suppressing internal execution error detailwarn / errorA client got internal execution error; this line has the real cause.
replication follower: ...warn / errorFollower progress problems; see Replication.
shutdown signal received; closing the store cleanlyinfoSIGTERM/SIGINT received.
raft replication is EXPERIMENTAL ...warnThe Raft Preview is enabled.

What to alert on​

AlertCondition (example)Severity
Node not ready/ready not 200 for 2 minpage
Durable publisher failed/ready reason durable publisher failedpage
Disk nearly fullfree space < 20% on the data filesystem (the write guard trips at 10% by default)page
Writes rejected for diskunavailable "free disk" errors (HTTP 503)page
Sheddingsustained 503 responses, or rushdb_scheduler_inflight / rushdb_scheduler_capacity > 0.9warn
Memoryrushdb_allocator_resident_bytes > 85% of the service's memory limitwarn
WAL growthrushdb_wal_retained_bytes > 75% of tx-log-retention-byteswarn
Archive gaplog WAL archive fell behind the retention cappage
Replica lagleader rushdb_commits_total − follower rushdb_commits_total above your tolerancewarn
Slow requestsrate of slow protocol call log lines, or p99 latency above targetwarn
Commit latencyp99 rushdb_commit_latency_seconds > 0.5 swarn
Internal errorsHTTP 500 responses or suppressing internal ... error detail lineswarn

See also​