Skip to main content
Authenticate and authorize requests to your AgentOS application using JWT tokens. The middleware extracts tokens from Authorization headers or cookies, validates them, and automatically injects user_id, session_id, and custom claims into your endpoints. The JWT middleware provides three main features:
  1. Token Validation: Validates JWT tokens and handles authentication
  2. Parameter Injection: Automatically injects user_id, session_id, and custom claims into endpoint parameters
  3. RBAC Authorization: Validates scopes against required permissions for each endpoint
jwt_middleware_setup.py
from agno.os.middleware import JWTMiddleware
from agno.os.middleware.jwt import TokenSource

app.add_middleware(
    JWTMiddleware,
    verification_keys=["your-jwt-verification-key"],  # or use JWT_VERIFICATION_KEY environment variable
    algorithm="RS256",  # RS256 for asymmetric keys, HS256 for symmetric
    user_id_claim="sub",  # Extract user_id from 'sub' claim
    session_id_claim="session_id",  # Extract session_id from claim
    dependencies_claims=["name", "email", "roles"],  # Additional claims
    validate=True,  # Enable token validation
    authorization=True,  # Enable RBAC scope checking
    verify_audience=True,  # Verify `aud` claim matches AgentOS ID
)

Token Sources

The middleware supports three token sources:
Extract JWT from Authorization: Bearer <token> header.
from agno.os.middleware.jwt import TokenSource

app.add_middleware(
    JWTMiddleware,
    verification_keys=["your-key"],
    token_source=TokenSource.HEADER,  # Default
)

JWKS File Support

For environments using RSA keys managed via JWKS (JSON Web Key Set), you can point to a static JWKS file instead of providing raw public keys:
jwks_file_setup.py
app.add_middleware(
    JWTMiddleware,
    jwks_file="/path/to/jwks.json",
    algorithm="RS256",
    authorization=True,
)
The middleware will:
  1. Load public keys from the JWKS file at startup
  2. Match incoming tokens by their kid (key ID) header claim
  3. Validate signatures using the appropriate key

JWKS File Format

The JWKS file should follow the standard format:
{
  "keys": [
    {
      "kty": "RSA",
      "kid": "my-key-id",
      "use": "sig",
      "alg": "RS256",
      "n": "0vx7agoebGc...",
      "e": "AQAB"
    }
  ]
}

Environment Variable

You can also set the JWKS file path via environment variable:
export JWT_JWKS_FILE="/path/to/jwks.json"
JWKS keys are tried first (matched by kid). If no matching key is found, the middleware falls back to verification_keys if provided.

Parameter Injection

The middleware automatically injects JWT claims into AgentOS endpoints. The following parameters are extracted from tokens and injected into requests:
  • user_id - User identifier from token claims
  • session_id - Session identifier from token claims
  • dependencies - Custom claims for agent tools
  • session_state - Custom claims for session management
For example, the /agents/{agent_id}/runs endpoint automatically uses user_id, session_id, dependencies, and session_state from the JWT token when available. This is useful for:
  • Automatically using the user_id and session_id from your JWT token when running an agent
  • Automatically filtering sessions retrieved from /sessions endpoints by user_id (where applicable)
  • Automatically injecting dependencies from claims in your JWT token into the agent run, which then is available on tools called by your agent
View the full example for more details.

Security Features

Use strong verification keys, store them securely (not in code), and enable validation in production.
Token Validation: When validate=True, the middleware:
  • Verifies JWT signature using the verification key
  • Checks token expiration (exp claim)
  • Returns 401 errors for invalid/expired tokens
Audience Verification: When verify_audience=True, the middleware:
  • If audience is provided, it will validate the token’s audience claim matches the expected audience claim
  • If audience is not provided, it will validate the token’s audience claim matches the AgentOS ID
  • Optionally set the audience_claim to validate a custom audience claim
  • Returns 401 for tokens with mismatched audience
HTTP-Only Cookies: When using cookies:
  • Set httponly=True to prevent JavaScript access (XSS protection)
  • Set secure=True for HTTPS-only transmission
  • Set samesite="strict" for CSRF protection

RBAC Authorization

Enable Role-Based Access Control (RBAC) to validate JWT scopes against required permissions:
jwt_with_rbac.py
app.add_middleware(
    JWTMiddleware,
    verification_keys=["your-jwt-key"],
    algorithm="RS256",
    authorization=True,  # Enable RBAC
    verify_audience=True,  # Verify aud matches AgentOS ID
)
When authorization=True, the middleware:
  • Checks the scopes claim in JWT tokens
  • Validates scopes against required permissions for each endpoint
  • Returns 403 Forbidden for insufficient permissions

Scope Format

FormatExampleDescription
resource:actionagents:readAccess all resources
resource:<id>:actionagents:my-agent:runAccess specific resource
resource:*:actionagents:*:runWildcard access
agent_os:adminagent_os:adminFull admin access

Custom Scope Mappings

Override or extend default scope mappings:
custom_scope_mappings.py
app.add_middleware(
    JWTMiddleware,
    verification_keys=["your-key"],
    authorization=True,
    scope_mappings={
        # Override default
        "GET /agents": ["custom:agents:list"],
        # Add new endpoint
        "POST /custom/action": ["custom:write"],
        # Allow without scopes
        "GET /public": [],
    }
)
For detailed RBAC documentation including all available scopes and default mappings, see RBAC Documentation.

Excluded Routes

Skip middleware for specific routes:
jwt_excluded_routes.py
app.add_middleware(
    JWTMiddleware,
    verification_keys=["your-key"],
    excluded_route_paths=[
        "/health",
        "/auth/login", 
        "/auth/register",
        "/public/*",  # Wildcards supported
    ]
)

Configuration Options

See the JWTMiddleware Reference for the complete list of configuration options.

Authentication Options

ParameterDescriptionDefault
verification_keysList of keys for JWT verification. For RS256, use public keys. For HS256, use shared secrets. Each key is tried in order until one succeeds.JWT_VERIFICATION_KEY env var
jwks_filePath to a static JWKS file containing public keys. Keys are matched by kid from the JWT header.JWT_JWKS_FILE env var
secret_key(Deprecated) Use verification_keys instead.-
algorithmJWT algorithm (RS256, HS256, ES256, etc.)"RS256"
validateEnable token validationTrue

Token Source Options

ParameterDescriptionDefault
token_sourceWhere to extract token from: HEADER, COOKIE, or BOTHTokenSource.HEADER
token_header_keyHeader key for Authorization (when using HEADER or BOTH)"Authorization"
cookie_nameCookie name (when using COOKIE or BOTH)"access_token"

Claim Extraction Options

ParameterDescriptionDefault
user_id_claimJWT claim for user ID"sub"
session_id_claimJWT claim for session ID"session_id"
scopes_claimJWT claim for scopes"scopes"
audience_claimJWT claim for audience/OS ID"aud"
dependencies_claimsList of claims to extract for dependencies parameter[]
session_state_claimsList of claims to extract for session_state parameter[]

Authorization Options (RBAC)

ParameterDescriptionDefault
authorizationEnable RBAC scope checkingFalse
verify_audienceVerify aud claim matches AgentOS IDFalse
audienceExpected audience claim to validate against the token’s audience claimAgentOS ID
scope_mappingsCustom route-to-scope mappings (additive to defaults)None
admin_scopeScope that grants full admin access"agent_os:admin"
excluded_route_pathsRoutes to skip JWT/RBAC checksSee below

Examples

External Resources