Skip to content

Key Configuration

This document explains how to create and configure RSA keys for the auth service’s token exchange feature.

The auth service uses RSA keys to sign enriched JWT tokens during token exchange. These tokens contain governance organization/project context, roles, DID key claims, and IDP metadata that may not be present in the original IDP token.

The service supports three methods for configuring RSA keys, in order of precedence:

Section titled “1. Environment Variable (Recommended for Production)”

Provide the private key directly via the AUTH_SERVICE_PRIVATE_KEY environment variable.

Terminal window
# Generate a 2048-bit RSA private key
openssl genrsa -out auth-service-key.pem 2048
# Set the environment variable with the key content
export AUTH_SERVICE_PRIVATE_KEY="$(cat auth-service-key.pem)"
# Optionally set a custom key ID (otherwise auto-generated)
export AUTH_SERVICE_KEY_ID="auth-service-prod-001"

Advantages:

  • No file system access required
  • Easy integration with secrets management systems
  • Suitable for containerized deployments

The service can read keys from a file path on the filesystem.

Terminal window
# Generate the key
openssl genrsa -out /secure/path/auth-service-key.pem 2048
# Set the path via environment variable
export AUTH_SERVICE_KEY_PATH="/secure/path/auth-service-key.pem"
# The service will automatically create a .kid file for the key ID

Default path: /tmp/auth-service-key.pem (if AUTH_SERVICE_KEY_PATH not set)

Advantages:

  • Keys persist across restarts
  • Can use existing key management workflows
  • Suitable for VM-based deployments

If no key is provided, the service automatically:

  • Generates a 2048-bit RSA key pair
  • Saves it to the configured or default path
  • Creates a unique key ID

Advantages:

  • Zero configuration for development
  • Quick setup for testing

Warning: Auto-generated keys may be lost on container restart if not using persistent storage.

  • Type: RSA private key
  • Size: 2048 bits (hardcoded in the service)
  • Format: PEM-encoded
  • Supported Encodings: PKCS1 or PKCS8
  • Signing Algorithm: RS256 (RSA with SHA-256)
  • Key ID Format: auth-service-{8-hex-chars} (auto-generated from the first UUID segment) or custom

The Auth Service Helm chart injects AUTH_SERVICE_PRIVATE_KEY and AUTH_SERVICE_KEY_ID from a templated Kubernetes Secret. Provision the key material through your secret manager of choice (AWS Secrets Manager, Azure Key Vault, GCP Secret Manager) and wire it into the release-specific Helm values rather than creating secrets out-of-band.

services:
auth-service:
image: auth-service:latest
environment:
AUTH_SERVICE_PRIVATE_KEY: |
-----BEGIN RSA PRIVATE KEY-----
MIIEpAIBAAKCAQEA...
-----END RSA PRIVATE KEY-----
AUTH_SERVICE_KEY_ID: auth-service-dev-001
Terminal window
# Generate private key
openssl genrsa -out auth-service-private.pem 2048
# Extract public key (for documentation/verification)
openssl rsa -in auth-service-private.pem -pubout -out auth-service-public.pem
# View key details
openssl rsa -in auth-service-private.pem -text -noout

Generate with Password Protection (convert before use)

Section titled “Generate with Password Protection (convert before use)”
Terminal window
# Generate encrypted key
openssl genrsa -aes256 -out auth-service-private-encrypted.pem 2048
# Remove password for service use
openssl rsa -in auth-service-private-encrypted.pem -out auth-service-private.pem
Terminal window
# PKCS1 to PKCS8
openssl pkcs8 -topk8 -inform PEM -outform PEM -nocrypt \
-in auth-service-private.pem -out auth-service-private-pkcs8.pem
# PKCS8 to PKCS1
openssl rsa -in auth-service-private-pkcs8.pem -out auth-service-private-pkcs1.pem

The public key is automatically exposed via the JWKS endpoint:

Terminal window
# Get the JWKS (JSON Web Key Set)
curl http://localhost:8080/api/v1/auth/.well-known/jwks.json
# Response format
{
"keys": [
{
"kty": "RSA",
"use": "sig",
"kid": "auth-service-prod-001",
"alg": "RS256",
"n": "...", // Modulus (base64url)
"e": "AQAB" // Exponent (base64url)
}
]
}

External services use this endpoint to validate tokens issued by the auth service.

  1. Generate new key pair

    Terminal window
    openssl genrsa -out auth-service-key-new.pem 2048
  2. Update configuration

    Terminal window
    export AUTH_SERVICE_PRIVATE_KEY="$(cat auth-service-key-new.pem)"
    export AUTH_SERVICE_KEY_ID="auth-service-prod-002" # New ID
  3. Deploy carefully

    • Rolling update in Kubernetes
    • Blue-green deployment
    • Gradual instance replacement
  4. Monitor

    • Old tokens remain valid until expiration
    • New tokens use the new key
    • The current JWKS endpoint exposes the active signing key only, so rotate during a window where old access tokens can expire naturally or downstream validators can tolerate the key change

If a key is compromised:

  1. Generate and deploy new key immediately
  2. Reduce token expiration time temporarily
  3. Force re-authentication where possible
  4. Monitor for unauthorized token usage
  1. Never commit private keys to version control
  2. Use secrets management systems in production:
    • Kubernetes Secrets
    • AWS Secrets Manager
    • HashiCorp Vault
    • Azure Key Vault
  3. Restrict file permissions to 0600 for key files
  4. Encrypt keys at rest in production environments
  1. Rotate keys periodically

    • Production: Every 90 days
    • Staging: Every 180 days
    • Development: As needed
  2. Monitor key usage through logs:

    grep "Issued enriched token" auth-service.log
  3. Audit key access in production environments

  1. Separate keys per environment (dev, staging, prod)
  2. Use different key IDs to track key usage
  3. Implement key escrow for disaster recovery
  4. Document key rotation procedures

Service fails to start with key error:

Error: failed to load or generate key: failed to parse private key
  • Check key format (must be PEM)
  • Verify no extra whitespace in environment variable
  • Ensure proper line endings (LF, not CRLF)

Token validation fails:

Error: token signature is invalid
  • Verify correct public key in JWKS
  • Check key ID matches between token and JWKS
  • Ensure token hasn’t been modified

Auto-generated key lost:

  • Check default path: /tmp/auth-service-key.pem
  • Look for backup in service logs
  • Generate new key and restart
Terminal window
# Verify key format
openssl rsa -in auth-service-key.pem -check
# Test key with sample JWT
echo '{"test": "data"}' | jwt encode -k auth-service-key.pem -a RS256
# Decode and verify token
jwt decode -k auth-service-public.pem YOUR_TOKEN
# Check JWKS endpoint
curl -s http://localhost:8080/api/v1/auth/.well-known/jwks.json | jq

When migrating from other token signing methods:

  1. Dual validation period: Support both old and new tokens
  2. Gradual rollout: Update services incrementally
  3. Monitor error rates: Track validation failures
  4. Communicate changes: Notify API consumers
  • Token Exchange - Overview of token exchange feature
  • Refresh Tokens - Refresh-token behavior for exchanged tokens
  • Auth Service API reference - generated from the service OpenAPI specification and available in the published docsite; Swagger UI is served at /swagger/ when enabled