Metrics & CLI
TL;DR — Two references in one page. Metrics — every counter/histogram/gauge AuthPlane emits, with the prefix (
authserver_*for legacy,authplane_*for Phase-3 features), the labels, and a one-line description. CLI — every command theauthserverbinary ships (serve,migrate,purge,admin *), with their flags and typical use. Same commands run under systemd, Docker, and Kubernetes.
Metrics catalog
Metrics are emitted via OpenTelemetry and can be scraped by Prometheus (observability.metrics.provider: prometheus, default /metrics path) or pushed to an OTLP endpoint (provider: otel or both). Full config in Configuration: observability, Prometheus + Grafana setup in Guides: Monitoring.
Prefix note
Metric names use two prefixes — a historical artifact:
authserver_*— original metrics (tokens, auth flow, OIDC, introspection, key management, upstream broker).authplane_*— Phase-3 additions (client credentials, DPoP, token exchange, agent identity, XAA).
Both are stable — dashboard once, don’t change. When grepping /metrics, remember to search both prefixes.
Counters (_total)
OAuth core
OIDC federation
Signing key management
Broker / upstream token vending
Client Credentials
DPoP (RFC 9449)
Token exchange (RFC 8693)
Agent identity + XAA
Admin API
HTTP
Histograms (_duration_seconds)
Recorded in seconds. Buckets: 0.001, 0.005, 0.01, 0.025, 0.05, 0.1, 0.25, 0.5, 1, 2.5, 5, 10.
Gauges
Recommended alerts
Start with these; tune thresholds to your traffic.
rate(authserver_auth_denied_total[5m]) > 10— spike in auth denials (possible attack or misconfig)rate(authserver_refresh_token_reuse_total[5m]) > 0— refresh-token theft detected (never expected in normal ops)rate(authplane_dpop_proofs_rejected_total[5m]) > 5— DPoP failures spiking (SDK misconfig or client bug)histogram_quantile(0.99, rate(authserver_token_issuance_duration_seconds_bucket[5m])) > 0.5— p99 token issuance > 500 ms (DB or Vault latency)authserver_key_rotation_total unchanged for 90d— rotation cadence missedauthserver_upstream_token_refresh_total{outcome="failed"} > 0— upstream provider auth broken
Full alert examples in Guides: Monitoring.
CLI reference
Every AuthPlane operational task can run from the CLI. Same binary as the server (authplane/authserver:latest or the standalone Linux binary). Config is passed as --config <path> or via AUTHPLANE_* env vars.
authserver serve
Start the server. Runs both public (:9000) and admin (:9001) HTTP servers.
authserver serve --config /etc/authserver/config.yaml
Flags:
--config <path>— YAML config file. Optional; without it, defaults + env vars are used.
Signal handling:
SIGTERM/SIGINT— graceful shutdown (drains forserver.shutdown_wait, default 10 s).SIGHUP— reload signing keys hot (current/previousJWKS refresh). No connection drop.
See Operate: Standalone for the systemd unit and Operate: Docker Compose for the container form.
authserver migrate
Apply pending database migrations. Idempotent — safe to re-run.
authserver migrate --config /etc/authserver/config.yaml
Migrations are embedded in the binary via go:embed and applied by serve on boot too — migrate is the standalone form for CI/CD pipelines that want to run migrations separately from the server process. Forward-only; there is no rollback.
The Helm chart’s init container waits for Postgres connectivity but does NOT run this — the main process handles migrations on pod boot.
authserver purge
Delete expired rows from the DB. Not run by serve; schedule externally.
authserver purge --config /etc/authserver/config.yaml
authserver purge --only=dpop-nonces,jti --timeout=5m
Flags:
--config <path>— YAML config (needed to reach the DB).--only <targets>— comma-separated list from:assertion-jti,connect-pending-states,dpop-nonces,jti,machine-tokens,refresh-tokens,sessions. Default: all targets.--timeout <duration>— abort after this duration. Default10m. Pass0to disable.
Exit codes — non-zero if any target fails or context canceled. Individual failures log at ERROR with table=<target> attribute; the command continues with remaining targets and fails at the end. Wire into your alerting.
Scheduling recipes for systemd, Docker Compose, and Kubernetes CronJob in Operate: Backup, upgrade, purge.
authserver version
Print the binary version and exit.
authserver version
# authserver v0.1.x commit=abcdef1 built=2026-01-01T00:00:00Z
authserver admin user create
Bootstrap the first admin user (before the Admin UI is reachable).
authserver admin user create \
--config /etc/authserver/config.yaml \
--email admin@example.com \
--password changeme \
--name Admin \
--role admin
Flags:
--email— user’s email (required)--password— initial password (required; change after first login)--name— display name (required)--role—adminoruser(defaultuser)
After the first admin exists, manage users via the Admin UI or authserver admin user *.
Admin CLI — authserver admin *
Every entity in the Admin API has a matching CLI verb. Common pattern:
authserver admin <entity> <verb> [--flags]
Auth uses the same AUTHPLANE_ADMIN_API_KEY as the REST API. Config path (for DB access) via --config or env.
admin client
OAuth client management.
authserver admin client list # list all
authserver admin client create --grant-types authorization_code,refresh_token \
--redirect-uris https://app.example.com/cb \
--scopes 'tools/read||Read tools' \
--scopes 'tools/write||Write tools' \
--auth-method client_secret_post \
--name "My App"
The CLI subcommands are list, create, update, rotate-secret, and delete. For get, suspend, and reactivate, use the admin REST API — for example:
# Inspect a client
curl -s http://localhost:9001/admin/clients/<client_id> \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
# Suspend a client (block new tokens)
curl -s -X PATCH http://localhost:9001/admin/clients/<client_id>/suspend \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
# Reactivate a suspended client
curl -s -X PATCH http://localhost:9001/admin/clients/<client_id>/reactivate \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
Output format: --json for JSON, default is key=value per line.
admin user
Local user management.
authserver admin user list
authserver admin user create --email … --password … --role admin
authserver admin user update --id <user_id> --email new@example.com
authserver admin user force-logout --id <user_id>
authserver admin user delete --id <user_id>
The CLI subcommands are list, create, update, delete, and force-logout. For get, disable, enable, and password resets, use the admin REST API — for example:
# Look up a user
curl -s "http://localhost:9001/admin/users?email=<email>" \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
# Disable a user (block logins)
curl -s -X PATCH http://localhost:9001/admin/users/<user_id>/disable \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
# Enable a user
curl -s -X PATCH http://localhost:9001/admin/users/<user_id>/enable \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
# Reset a user's password (field on the generic update endpoint)
curl -s -X PATCH http://localhost:9001/admin/users/<user_id> \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY" \
-H "Content-Type: application/json" \
-d '{"password":"<new>"}'
admin resource
Mint / Broker resources.
authserver admin resource list
authserver admin resource get --slug <slug>
authserver admin resource create --slug my-mcp \
--uri http://localhost:3000/mcp \
--backend-kind mint \
--scope-map "tools/read:tools/read,tools/write:tools/write"
authserver admin resource update --slug my-mcp --scopes 'tools/read||Read tools' --scopes 'tools/write||Write tools' --scopes 'tools/delete||Delete tools'
authserver admin resource delete --slug my-mcp
Broker resources include --broker-provider <id> (identifies the upstream provider). Per-resource policy (policy.exchange.allowed_client_ids, policy.runtime.client_ids, policy.connect.allowed_return_urls) has dedicated subcommands under admin resource policy.
admin provider
Broker providers (upstream OAuth / API key / service account).
authserver admin provider list
authserver admin provider get --id <id>
authserver admin provider create --slug github --protocol oauth \
--display-name "GitHub" \
--config-data ./github-provider.json
authserver admin provider update --id <id> --config-data ./github-provider.json
authserver admin provider delete --id <id>
admin grant
Consent grants + broker grants (per-user).
authserver admin grant list-user-grants --user <user_id>
authserver admin grant revoke-consent --id <consent_grant_id> # cascades onto live Mint issuances
authserver admin grant revoke-broker --id <broker_grant_id> # no issuance cascade — upstream tokens are not AS-revocable
admin issuance
Per-token forensic audit rows.
authserver admin issuance list --user <user_id> # last N issuances for a user
authserver admin issuance list --client <client_id> --limit 50
authserver admin issuance list --resource <slug> --since 7d # Go-duration form (e.g. 24h, 7d; max 30d)
authserver admin issuance get --id <issuance_id>
admin key
Signing key management.
authserver admin key list # current + previous kids
authserver admin key rotate # zero-downtime rotation
Same as POST /admin/keys/rotate via the REST API. On multi-instance deployments with postgres_key or vault_transit, propagation is automatic via LISTEN/NOTIFY (ms). Single-instance keyfile may want SIGHUP after rotation.
admin dcr
Runtime DCR mode toggle. Persisted; survives restart.
authserver admin dcr get # show current mode
authserver admin dcr set --mode admin_only # switch modes at runtime
Modes: open, approved_redirects, admin_only. See Configuration: dcr.
XAA (Enterprise-Managed Auth) — no CLI subcommand; use the admin REST API
Trusted IdPs, XAA policies, and subject mappings have no authserver admin xaa … CLI equivalent. Manage them through the admin REST API:
# Trusted IdPs
curl -s http://localhost:9001/admin/idps \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
curl -s -X POST http://localhost:9001/admin/idps \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY" \
-H "Content-Type: application/json" \
-d '{"issuer":"https://idp.example.com","audience":"https://auth.example.com","jwks_uri":"https://idp.example.com/.well-known/jwks.json"}'
curl -s -X POST http://localhost:9001/admin/idps/<idp_id>/refresh-keys \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
curl -s -X DELETE http://localhost:9001/admin/idps/<idp_id> \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
# Policies
curl -s http://localhost:9001/admin/xaa/policies \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
curl -s -X POST http://localhost:9001/admin/xaa/policies \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY" \
-H "Content-Type: application/json" \
-d '{"idp_id":"<id>","client_ids":["<client>"],"scopes":["tools/read"],"resources":["https://mcp.example.com/mcp"]}'
curl -s -X DELETE http://localhost:9001/admin/xaa/policies/<policy_id> \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
# Subject mappings
curl -s http://localhost:9001/admin/xaa/subject-mappings \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY"
curl -s -X POST http://localhost:9001/admin/xaa/subject-mappings \
-H "Authorization: Bearer $AUTHPLANE_ADMIN_API_KEY" \
-H "Content-Type: application/json" \
-d '{"idp_id":"<id>","mode":"explicit","federated_subject":"foo","local_subject":"bar"}'
Only available when xaa.enabled: true.
admin fronting (advanced)
Fronting-link management for gateway topologies. See Topologies: MCP gateway → hidden Mint.
authserver admin fronting list
authserver admin fronting create --source <slug> --target <slug> \
--scope-map "src/read:dst/read"
authserver admin fronting delete --source <slug> --target <slug>
Global CLI flags
Every subcommand accepts:
--config <path>— YAML config path (or setAUTHPLANE_*env vars)--json— machine-readable output (default:key=valuelines)--help— subcommand help
Related
- Reference: Admin API — the REST equivalent of every
admin *command - Reference: Configuration — env vars + YAML keys that these commands operate on
- Guides: Monitoring — Prometheus scrape config, Grafana dashboards, alerting rules
- Guides: Admin API — task-focused walkthroughs
- Operate: Backup, upgrade, purge —
purgescheduling recipes