Unkey services read configuration from a TOML file passed at startup. Environment variables can be referenced with ${VAR} and are expanded before parsing. Defaults and validation run after parsing.The config schema maps to svc/api/config.go.Minimal config example:
Ordered authentication resolver configuration. Each entry registers one auth
mechanism. At least one entry is required: a config without auth entries
would reject every request, including valid root keys, so startup fails
instead.
Expected JWT iss claim. Required for type = "jwt" entries and rejected
as an unknown field on portal_session and root_key entries. The issuer
does not affect permission translation; set auth.provider to opt into
WorkOS slug translation.
Permission dialect carried by this entry’s tokens for type = "jwt".
Leave unset when tokens already carry canonical Unkey permissions. Set
provider = "workos" to translate WorkOS permission slugs into canonical
Unkey permissions after verification. Translation is selected by this
field, not inferred from the issuer, so any issuer (including custom auth
domains) can opt in the same way.
Optional expected JWT aud claim for type = "jwt". Verification
requires the configured value to appear in the token’s aud list. The
Unkey WorkOS environment uses a JWT template that sets aud to
["app.unkey.com", "api.unkey.com"], so set
audience = "api.unkey.com" on the WorkOS entry. Omit this field only
for providers that do not emit an audience claim. Setting it rejects
tokens without a matching aud, so when introducing the claim, add it
to the provider’s token template first, wait for tokens minted without
it to expire, then set this field.
Ordered JWT verification secrets for type = "jwt". During
rotation, put the active signing secret first and keep retired secrets
later in the list until every token signed with those secrets has expired.
Configure either secrets or jwks_url, never both.
JWKS endpoint for type = "jwt". Must be an absolute https URL so
signing keys cannot be substituted over an unauthenticated channel. The
API fetches the JSON Web Key Set on first use and verifies incoming JWTs
against usable RSA signing keys from the response. When a token fails
verification against every cached key, the key set is refetched (rate
limited to once per minute), so signing-key rotations are picked up
without a restart. Configure either jwks_url or secrets, never both.
The dashboard proxy forwards the WorkOS access token when a WorkOS session is
available. The API verifies that token through a type = "jwt" auth entry
configured with the WorkOS issuer and JWKS URL. The WorkOS JWT template includes
the organization as org.id, and the API reads Unkey RBAC permissions from the
token’s permissions claim. The template also sets aud to
["app.unkey.com", "api.unkey.com"], and the auth entry pins
audience = "api.unkey.com".Local development still uses a dashboard-minted fallback JWT when no WorkOS
access token exists. For that path, the dashboard needs a signing secret and the
API must include the same secret in a type = "jwt" auth entry. The local
fallback JWT includes the dashboard proxy permission set directly, so every
local dashboard user is effectively an API admin.
Local dashboard proxy signing secret. Add the same value to the API JWT auth
entry’s secrets list so the API can verify dashboard-minted fallback JWTs.