OIDC Authentication
OpenID Connect (OIDC) provides interactive browser authentication with single sign-on (SSO) capabilities. This guide covers OIDC setup, configuration, and troubleshooting.
Overview
Keyline implements the OIDC Authorization Code Flow with PKCE (Proof Key for Code Exchange) for secure authentication. This flow is suitable for public clients (browser-based applications).
Supported OIDC Providers
Keyline works with any OIDC-compliant identity provider including:
- Google Workspace
- Azure AD (Entra ID)
- Okta
- Auth0
- Keycloak
- Any generic OIDC provider
See Provider Setup Guides for configuration examples.
Configuration
Basic OIDC Configuration
oidc:
enabled: true
issuer_url: https://accounts.google.com
client_id: ${OIDC_CLIENT_ID}
client_secret: ${OIDC_CLIENT_SECRET}
redirect_url: https://auth.example.com/auth/callback
scopes:
- openid
- email
- profile
user_identity_claim: email
Configuration Options
| Option | Required | Description |
|---|---|---|
enabled | No | Enable OIDC authentication (default: false) |
issuer_url | Yes (if enabled) | OIDC provider issuer URL (must be HTTPS) |
client_id | Yes (if enabled) | OAuth2 client ID |
client_secret | Yes (if enabled) | OAuth2 client secret |
redirect_url | Yes (if enabled) | OAuth2 callback URL (must be HTTPS) |
scopes | No | OAuth2 scopes to request (default: openid, email, profile) |
user_identity_claim | No | Claim to use as ES username (default: email) |
OIDC Flow with PKCE
Step-by-Step Flow
Security Features
| Feature | Purpose |
|---|---|
| State Token | CSRF protection, single-use, 5-minute TTL |
| PKCE | Prevents authorization code interception |
| ID Token Validation | Signature, issuer, audience, expiration |
| JWKS Cache | Public key caching with 24h refresh |
Provider Setup Guides
Google Workspace Setup
Step 1: Create OAuth2 Credentials
- Go to Google Cloud Console
- Create a new project or select existing
- Enable "Google+ API"
- Go to "Credentials" → "Create Credentials" → "OAuth2 Client ID"
- Application type: Web application
- Add authorized redirect URI:
https://auth.example.com/auth/callback - Note the Client ID and Client Secret
Step 2: Configure Keyline
oidc:
enabled: true
issuer_url: https://accounts.google.com
client_id: 123456789-abc123def456.apps.googleusercontent.com
client_secret: ${GOOGLE_CLIENT_SECRET}
redirect_url: https://auth.example.com/auth/callback
scopes:
- openid
- email
- profile
user_identity_claim: email
Step 3: Configure Domain-Wide Delegation (Optional)
For Google Workspace domains, you can restrict access by domain:
oidc:
# ... other config
hd: example.com # Hosted domain restriction
Azure AD (Entra ID) Setup
Step 1: Register Application
- Go to Azure Portal
- Navigate to "Azure Active Directory" → "App registrations"
- Click "New registration"
- Name:
Keyline - Supported account types: Accounts in this organizational directory only
- Redirect URI:
https://auth.example.com/auth/callback(Platform: Web) - Click "Register"
Step 2: Configure Authentication
- In app registration, go to "Authentication"
- Under "Implicit grant", check:
- ID tokens (used for implicit flow)
- Click "Save"
Step 3: Create Client Secret
- Go to "Certificates & secrets"
- Click "New client secret"
- Description:
Keyline Secret - Expires: Choose duration
- Click "Add"
- Copy the secret value immediately (won't be shown again)
Step 4: Configure Keyline
oidc:
enabled: true
issuer_url: https://login.microsoftonline.com/{tenant-id}/v2.0
client_id: ${AZURE_CLIENT_ID}
client_secret: ${AZURE_CLIENT_SECRET}
redirect_url: https://auth.example.com/auth/callback
scopes:
- openid
- email
- profile
- offline_access
user_identity_claim: email
Okta Setup
Step 1: Create Application
- Go to Okta Admin Console
- Navigate to "Applications" → "Create App Integration"
- Sign-in method: OIDC - OpenID Connect
- Application type: Web application
- Click "Next"
Step 2: Configure Application
- Application name:
Keyline - Grant type: Authorization Code
- Sign-in redirect URI:
https://auth.example.com/auth/callback - Sign-out redirect URI:
https://auth.example.com/auth/logout
Step 3: Configure Keyline
oidc:
enabled: true
issuer_url: https://{your-org}.okta.com/oauth2/default
client_id: ${OKTA_CLIENT_ID}
client_secret: ${OKTA_CLIENT_SECRET}
redirect_url: https://auth.example.com/auth/callback
scopes:
- openid
- email
- profile
- groups
user_identity_claim: email
Claim Mapping
Extract User Identity
The user_identity_claim determines which claim becomes the ES username:
oidc:
user_identity_claim: email # Common choices: email, sub, preferred_username
Common Claims
| Claim | Description | Example |
|---|---|---|
sub | Unique identifier | 1234567890 |
email | Email address | user@example.com |
preferred_username | Display username | john.doe |
name | Full name | John Doe |
groups | Group memberships | ["admin", "users"] |
Troubleshooting
Discovery Document Fetch Failed
Error: Failed to fetch OIDC discovery document
Solution:
- Verify
issuer_urlis correct and accessible - Check network connectivity from Keyline to OIDC provider
- Test discovery endpoint manually:
curl https://accounts.google.com/.well-known/openid-configuration
Redirect URI Mismatch
Error: Redirect URI mismatch from OIDC provider
Solution:
- Verify
redirect_urlexactly matches configured URI in OIDC provider - Ensure HTTPS is used (required by most providers)
- Check for trailing slashes
Invalid State Token
Error: Invalid or expired state token
Solution:
- Check session storage is working (Redis/memory)
- Verify
session_secretis configured - Ensure cookies are being transmitted correctly
ID Token Validation Failed
Error: Invalid token signature or Invalid token claims
Solution:
- Verify
issuer_urlmatches theissclaim - Verify
client_idmatches theaudclaim - Check system time is synchronized (NTP)
- Test JWKS endpoint accessibility
Next Steps
- Local Users (Basic Auth) - Configure Basic Authentication
- Session Management - Session storage configuration
- Role Mappings - Map OIDC claims to ES roles