Skip to main content
Unkey Deploy is currently in private beta. To get access, reach out on Discord or email support@unkey.com.
JWT authentication is coming soon. The Principal format is documented here so you can plan your integration.
When the Principal’s type is "jwt", the source.jwt object contains the full decoded JWT, mirroring the three-part structure of a JWT token (header, payload, signature). The Sentinel forwards everything without renaming or filtering.

Fields

source.jwt.header
object
required
The decoded token header. Contains the signing algorithm, token type, and key identifier used to verify the token. Common fields include alg (for example, "RS256"), typ (typically "JWT"), and kid (the key ID used for signature verification, useful for tracking key rotation).
source.jwt.payload
object
required
The decoded token payload with all claims as-is, using their original JWT claim names and types. Registered claims like iss, sub, aud, exp, iat, nbf, and jti appear alongside any custom claims from your identity provider (for example, org_id, email, scope).Common registered claims (RFC 7519):
ClaimTypeDescription
issstringThe token issuer
substringThe token subject (also used as the top-level subject)
audstringThe intended audience
expintegerExpiration time (Unix timestamp in seconds)
nbfintegerNot valid before (Unix timestamp in seconds)
iatintegerIssued at (Unix timestamp in seconds)
jtistringUnique token identifier
source.jwt.signature
string
required
The raw signature string from the token’s third segment. The Sentinel has already verified this signature, so your app doesn’t need to verify it again. Useful for audit logging or correlating requests back to a specific token.

Examples

Because the Sentinel forwards the raw JWT payload, the Principal contains exactly the claims your identity provider includes in the token. Here are examples for common providers.
{
  "version": 1,
  "subject": "user_01JCQ1E9ZV4JQXNCT0TD4V7DJ3",
  "type": "jwt",
  "source": {
    "jwt": {
      "header": {
        "alg": "RS256",
        "kid": "sso_oidc_key_pair_01HRSF8B...",
        "typ": "JWT"
      },
      "payload": {
        "iss": "https://api.workos.com/user_management/client_01HRSF8B1GR4T5GCG0F9GN9GBV",
        "sub": "user_01JCQ1E9ZV4JQXNCT0TD4V7DJ3",
        "aud": "client_01HRSF8B1GR4T5GCG0F9GN9GBV",
        "exp": 1711310400,
        "iat": 1711306800,
        "nbf": 1711306800,
        "sid": "session_01JCQ1F4WP3AX8M0QVZGKE6CRP",
        "org_id": "org_01HBFNK8TBB76Y5M3QAG8W9J0V",
        "role": "admin",
        "permissions": ["deploy:create", "deploy:delete", "settings:manage"],
        "entitlements": ["advanced-analytics", "custom-domains"]
      },
      "signature": "dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW..."
    }
  }
}
Each provider structures its claims differently. WorkOS uses role and permissions at the top level. Clerk v2 nests organization data under an o object with abbreviated keys (rol, per, slg). Auth0 uses scope as a space-delimited string, requires namespaced custom claims, and returns aud as an array when openid scope is requested. Because the Sentinel passes the payload through as-is, your app receives exactly what your auth provider issued without Unkey needing provider-specific logic.
Last modified on March 30, 2026