Operations endpoints sit at the site root rather than under /api/v1. /health answers whether the Phoenix application is alive, /ready checks PostgreSQL, migrations, and configured Oban queues, and production /metrics requires its own dedicated bearer token.
Liveness and readiness answer different questions
A 200 from /health means the web process can answer. /ready additionally queries the repository, checks for down migrations, and verifies every configured Oban queue is active with positive concurrency; unhealthy dependencies make it return 503.
Metrics has a separate trust boundary
The metrics token is neither an agk_ workspace key nor an operator session. Production requires metrics auth and refuses startup without a nonblank configured token; invalid scrapes return 401 with a Bearer challenge.
Probe responses are not cached
Health, readiness, and metrics responses set no-cache/no-store controls so monitors observe current process state. The JSON timestamps are probe times, not deployment-version markers.
Before you begin
The command-line examples require curl and jq; any exception is identified in its introduction.
Network access from the load balancer or monitoring system to the root probe paths.
A separately managed METRICS_BEARER_TOKEN for production metrics scraping.
Probe timeouts and alerting rules that preserve the HTTP status instead of checking only response text.
How it works
Route liveness conservatively
Use GET /health for process restart decisions. Do not make database or worker incidents cause liveness restarts; those dependencies belong to readiness.
Gate traffic and deploys on readiness
Use GET /ready before adding an instance to service and after migrations. Parse checks.repo, checks.migrations, and checks.oban to identify the failing dependency.
Scrape metrics with the dedicated secret
Send Authorization: Bearer $METRICS_BEARER_TOKEN to /metrics, store the token in the monitoring platform's secret facility, and never substitute a workspace API key.
Examples
These examples are illustrative. Replace the sample values with your own.
Keep credentials in environment variables or a secret manager, never in client-side code.
Check readiness and scrape metrics
The script fails on non-2xx responses and keeps the metrics credential separate from machine API credentials.
Healthy liveness/readiness calls return 200 JSON. Metrics returns 200 text/plain in Prometheus exposition format; an unhealthy required readiness check returns 503 with its check map.
Troubleshooting
Health is 200 while readiness is 503
The process is alive but PostgreSQL, migration state, or an Oban queue is unhealthy. Use the readiness checks object; restarting solely because of dependency failure can amplify an outage.
Readiness reports migrations pending
Apply the release migrations before routing traffic. A pending migration is not considered degraded or healthy by this endpoint.
Metrics returns 401
Use the dedicated configured metrics bearer exactly, without an agk_ prefix assumption. Check for the WWW-Authenticate: Bearer realm="metrics" response and secret drift between app and scraper.
Endpoint reference
Ready to integrate? Open an endpoint for its required permissions, request fields,
response format, and status codes. The examples above explain the workflow;
these details define each individual request.
GET
/health
Application liveness
Description
Returns no-cache JSON when the Phoenix application is running. This is a liveness probe; use /ready for dependency checks.
Auth
None
Responses
200
Application process is alive
Response Body
Field
Type
Required
Description
status
string
Yes
ok
timestamp
string
Yes
ISO 8601 probe time
GET
/ready
Application readiness
Description
Checks PostgreSQL connectivity, pending Ecto migrations, and the required Oban queues. Returns 503 when any required check is unhealthy.
Auth
None
Responses
200
Dependencies are ready
Response Body
Field
Type
Required
Description
status
string
Yes
ok or degraded
timestamp
string
Yes
ISO 8601 probe time
checks
object
Yes
repo, migrations, and oban results
503
At least one required dependency is unhealthy
GET
/metrics
Metrics Token
Prometheus metrics
Description
Returns a no-cache Prometheus text export. Metrics bearer authentication is mandatory in production and requires Authorization: Bearer {METRICS_BEARER_TOKEN}.