Skip to content

aegis · Get started

Configuration

Every aegis setting is an environment variable. This reference lists all 77 variables by subsystem, with defaults and production guidance.

On this page

How configuration works#

You configure aegis entirely through environment variables. The gateway takes no command-line flags and reads no configuration file. Its own code reads the 77 variables in the reference tables below; the AWS SDK behind the credential broker also reads the standard AWS variables. Each optional subsystem stays off until the variables it needs are set.

To turn a feature off, unset its variable rather than setting it to an empty string. Many variables treat an empty value as set: an empty AUTH_ALLOWED_TENANTS refuses every tenant, and an empty DATABASE_URL still switches the gateway to the Postgres catalog. The Helm chart omits empty values for this reason.

Most subsystems log their state at startup, for example Auth: DISABLED, RBAC DISABLED (no DATABASE_URL) or Audit log DISABLED (no CLICKHOUSE_URL). Read that log after each change to confirm what is actually on.

Two stores are checked before the gateway serves traffic. It connects to Redis at startup and exits if it cannot. When DATABASE_URL is set, it tries to load the catalog 10 times, 2 seconds apart, and exits if Postgres is still unreachable. ClickHouse is not checked this way: if the audit schema cannot be set up at startup, the gateway starts with the audit log off and logs Audit log DISABLED, so look for that line after every deploy.

A production baseline looks like this. Replace every placeholder, and supply the secret values from your secret store rather than from a file in source control.

bash
REDIS_URL=redis://redis:6379
DATABASE_URL=postgres://USER:PASSWORD@postgres:5432/DBNAME
CLICKHOUSE_URL=http://clickhouse:8123
AUDIT_HMAC_KEY=REPLACE_WITH_A_LONG_RANDOM_SECRET
AUTH_JWKS_URL=https://idp.example.com/.well-known/jwks.json
AUTH_ISSUER=https://idp.example.com/
AUTH_AUDIENCE=aegis
METRICS_TOKEN=REPLACE_WITH_A_RANDOM_TOKEN

Variable reference#

Core and stores#

VariableDefaultPurpose
REDIS_URLredis://127.0.0.1:6379Sessions, rate limits and kill-switch state. Required.
DATABASE_URLunsetPostgres. Enables the server catalog, RBAC and approvals. If unset, the gateway runs a single upstream with RBAC off.
UPSTREAM_URLhttp://localhost:9000The single upstream. Used only when DATABASE_URL is unset.
CLICKHOUSE_URLunsetClickHouse HTTP endpoint. Enables the audit log.
CLICKHOUSE_DBaegisAudit database name.
MCP_PROTOCOL_VERSION2025-06-18MCP revision the gateway declares to upstreams.
CATALOG_RECONCILE_SECS30How often routing is compared with the catalog and rebuilt on drift. 0 disables.
POLICY_REFRESH_SECS30Maximum age of the cached RBAC snapshot before it is re-read from Postgres. Role and policy changes take effect within this window.
APPROVAL_TTL_SECS3600Window, counted from when a held call was first requested, in which an approval can be used or a denial still applies.
KILLSWITCH_REFRESH_SECS2How often each replica reloads kill-switches from Redis.

Authentication#

VariableDefaultPurpose
AUTH_HS256_SECRETunsetAdds an HS256 shared-secret verifier. Meant for development and CI.
AUTH_JWKS_URLunsetAdds an RS256 verifier that fetches signing keys from your identity provider.
AUTH_ISSUERunsetRequired iss for the JWKS verifier. A token without the claim is rejected.
AUTH_AUDIENCEunsetRequired aud for the JWKS verifier, enforced the same way.
AUTH_SUBJECT_CLAIMsubClaim that holds the caller's subject, for example oid for Entra ID.
AUTH_TENANT_CLAIMtenantClaim that holds the tenant. A token without it belongs to tenant default.
AUTH_ALLOWED_TENANTSunsetComma-separated tenants this instance serves. Unset serves every tenant. Set but empty refuses every tenant.

Verifiers are tried in order (HS256, then JWKS, then the gateway's own issuer when OAUTH_ISSUER is set), and the first one that validates wins. Each verifier pins its algorithm, so an HS256 token can never pass an RS256 verifier. AUTH_ISSUER and AUTH_AUDIENCE scope the JWKS verifier only. With no verifier configured, authentication is off and every caller runs as anonymous in tenant default.

Rate limits#

VariableDefaultPurpose
RATE_LIMIT_PER_SESSION120Tool calls per minute per session. 0 disables.
RATE_LIMIT_PER_TOOL60Tool calls per minute per session and tool. 0 disables.

Limits use fixed one-minute windows in Redis. A limited call gets HTTP 429 with -32029. If Redis is unreachable, the limiter lets calls through.

Threat detection#

VariableDefaultPurpose
THREAT_MODEunset (enforce)monitor logs findings without blocking and downgrades PII and egress handling to monitor. Any other value enforces.
INPUT_VALIDATIONenforceChecks tools/call arguments against the tool's inputSchema. off, monitor or enforce.
PII_ACTIONredactResponse handling. redact masks hits as [REDACTED:KIND], block refuses a response that carries a credential, card number or SSN with -32052, monitor only logs.
PII_CLASSESunsetReplaces the default detector set with a comma-separated list, or all. PHONE and DATE_OF_BIRTH run only when listed or with all.
PII_CLASSES_EXCLUDEunsetClasses to remove, for example EMAIL for a search-by-email tool.
EGRESS_ACTIONblockSensitive values in outbound tool arguments. block refuses a call that carries a credential, card number or SSN with -32053; monitor only logs; off skips the scan. There is no redact mode.
INJECTION_SHELL_TOOLSemptyTool-name globs that also get the 8 ambiguous shell patterns. A trailing * matches a prefix; * alone matches every tool.
INTEGRITY_RESWEEP_SECS15How often upstreams are re-listed to check pinned tool definitions. 0 disables.
SHADOW_SWEEP_SECS60Interval of the report-only shadow and typosquat sweep. 0 disables the periodic sweep.

Audit#

VariableDefaultPurpose
AUDIT_HMAC_KEYbuilt-in development keyKeys the HMAC-SHA256 audit chain. The key never reaches ClickHouse. Required in production. If unset, the gateway uses a development key and logs an error at startup.

Upstream resilience and TLS#

VariableDefaultPurpose
CIRCUIT_FAILURE_THRESHOLD5Consecutive failures that open the breaker for one tenant and upstream.
CIRCUIT_COOLDOWN_SECS10How long the breaker stays open before one half-open probe.
UPSTREAM_MAX_CONCURRENT64In-flight calls per tenant and upstream. 0 disables.
UPSTREAM_MAX_RETRIES2Retries for connection-phase failures only.
UPSTREAM_TIMEOUT_SECS10Upstream deadline. A timeout after the request was sent returns -32064, because the tool may have run. 0 is ignored and the default applies.
UPSTREAM_MTLS_CERT_FILE, UPSTREAM_MTLS_CERT_PEMunsetClient certificate chain presented to https:// upstreams.
UPSTREAM_MTLS_KEY_FILE, UPSTREAM_MTLS_KEY_PEMunsetPrivate key for that certificate. Set it together with the certificate.
UPSTREAM_CA_FILE, UPSTREAM_CA_PEMunsetExtra CAs to trust for upstream server certificates.

An open breaker or a full concurrency cap fails fast with -32063. For each mTLS pair, a _FILE path takes precedence over the inline _PEM value. The settings apply to every https:// upstream and have no effect on http:// upstreams. If they are set but invalid, for example a certificate without its key, the gateway refuses to start rather than falling back to plain TLS.

Metrics#

VariableDefaultPurpose
METRICS_TOKENunset/metrics requires Authorization: Bearer with this value. Preferred.
METRICS_PUBLICunset1 or true serves /metrics without authentication. Use it only when the endpoint is isolated at the network layer.

With neither variable set, /metrics returns 503. When both are set, the token applies.

Commercial modules#

VariableDefaultPurpose
OAUTH_ISSUERunsetEnables OAuth 2.1 issuance (authorization code with PKCE S256) and sets iss.
OAUTH_AUDIENCEvalue of OAUTH_ISSUERaud of issued tokens.
OAUTH_CLIENT_IDaegis-cliClient ID the issuer accepts.
OAUTH_REDIRECT_URIShttp://localhost/callbackComma-separated allowed redirect URIs.
OAUTH_SIGNING_KEY_PEMgenerated at startupRS256 signing key (PKCS#8 RSA). A generated key does not survive a restart or work across replicas.
OAUTH_TOKEN_TTL_SECS3600Lifetime of issued tokens.
OAUTH_DEV_AUTHORIZEunset1 lets /oauth/authorize accept a subject with no login. Development only.
SCIM_BEARER_TOKENunsetEnables the SCIM 2.0 receiver for one tenant. Needs DATABASE_URL.
SCIM_TENANTdefaultTenant that SCIM_BEARER_TOKEN provisions into.
SCIM_BEARER_TOKENSunsetComma-separated tenant:token pairs, one per identity provider.
BROKER_ENABLEDunset1 or true enables the credential broker (AWS Secrets Manager).
BROKER_CACHE_TTL_SECS300How long a fetched secret is reused.
AWS_REGIONus-east-1Secrets Manager region.
AWS_ENDPOINT_URLunsetEndpoint override, for example LocalStack in development.
SPLUNK_HEC_URL, SPLUNK_HEC_TOKENunsetSplunk HTTP Event Collector sink. Both are required.
DATADOG_LOGS_URL, DATADOG_API_KEYunsetDatadog Logs sink. Both are required.
OTLP_LOGS_URLunsetOTLP/HTTP logs sink.
SIEM_WEBHOOK_URLunsetGeneric webhook sink.
SLACK_WEBHOOK_URLunsetSlack alerts. Treat the URL as a secret.
PAGERDUTY_ROUTING_KEYunsetPagerDuty alerts.
PAGERDUTY_EVENTS_URLhttps://events.pagerduty.com/v2/enqueuePagerDuty Events endpoint.
ALERT_WEBHOOK_URLunsetGeneric webhook alerts.
ALERT_COOLDOWN_SECS300Quiet period for a repeated alert on the same kind, tenant, server and tool.
BILLING_ENABLEDunset1 or true enables per-tenant monthly metering and tier quotas. Needs DATABASE_URL and STRIPE_WEBHOOK_SECRET.
BILLING_ENFORCE01 refuses over-quota calls with HTTP 402 and -32060. 0 counts and lets calls through.
BILLING_REFRESH_SECS30Tier snapshot refresh interval.
BILLING_TIER_FREE_QUOTA10000Monthly tool calls on Free, the tier for unknown tenants. 0 is unlimited.
BILLING_TIER_GROWTH_QUOTA1000000Monthly tool calls on Growth.
BILLING_TIER_ENTERPRISE_QUOTA0Monthly tool calls on Enterprise. 0 is unlimited.
STRIPE_WEBHOOK_SECRETunsetWebhook signing secret, comma-separated for rotation. Billing stays off while it is empty.
STRIPE_WEBHOOK_TOLERANCE_SECS300Webhook replay window.
STRIPE_PRICE_GROWTH, STRIPE_PRICE_ENTERPRISEunsetStripe price IDs mapped to tiers. An unknown price never grants a tier.

The broker reads AWS credentials from the standard AWS credential chain, such as AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY or an IAM role provided by your platform. Federated login for /oauth/authorize is not implemented yet. Without OAUTH_DEV_AUTHORIZE, that endpoint returns 501.

Production checklist#

Put these settings in place before the gateway receives real traffic:

  • Configure at least one verifier. With none, every caller runs as anonymous.
  • Prefer AUTH_JWKS_URL with AUTH_ISSUER and AUTH_AUDIENCE. Unset AUTH_HS256_SECRET entirely, not just to an empty string. Every configured verifier is accepted, so anyone holding the shared secret could sign a token for any subject.
  • Set DATABASE_URL so the catalog and RBAC are enforced.
  • Set CLICKHOUSE_URL and a strong, random AUDIT_HMAC_KEY, then confirm the startup log reports the audit log as enabled.
  • Set METRICS_TOKEN rather than METRICS_PUBLIC.
  • Keep the stores private. Put Redis, Postgres and ClickHouse on a network segment that only the gateway can reach, and connect with the redis://, postgres:// and http:// URL forms shown in the baseline.
  • Keep logging at info. The gateway sets its log level to info in code and does not read RUST_LOG. If you raise it in your own build, keep production at info, because HTTP client wire logging at debug and trace can include header values.
  • Never set OAUTH_DEV_AUTHORIZE. If you use OAuth issuance, set a stable OAUTH_SIGNING_KEY_PEM.
  • Keep secret values out of source control. In the Helm chart, prefer pointing secrets.existingSecret at a Secret you manage, for example through an external secrets operator. If you pass values to the chart instead, use --set or a values file kept out of git. Put DSNs that embed a password under secrets.*, not config.*, which renders a plaintext ConfigMap.