← Back to Demo

Keycloak HA Demo

High-Level Architecture & Testing Guide

Architecture Testing Guide Keycloak Failover Data Grid Cache Mode PostgreSQL HA JWT Viewer

High-Level Design

HTTPS Clients HAProxy HTTP Load Balancer :443 PostgreSQL Proxy :5432 Coupled health check: Patroni /primary + Keycloak /realms/master SHARED SERVICES etcd (DCS) 389-ds LDAP Site-A MicroShift (K8s) Keycloak (RHBK 26.4) Data Grid 8.5 PostgreSQL 17 Patroni (HA manager) Active when pg-a = Leader (HTTP + DB coupled to same site) ACTIVE or STANDBY Site-B MicroShift (K8s) Keycloak (RHBK 26.4) Data Grid 8.5 PostgreSQL 17 Patroni (HA manager) Active when pg-b = Leader (HTTP + DB coupled to same site) ACTIVE or STANDBY HTTPS :443 TCP :5432 Cache SYNC Streaming Replication (WAL)
HTTPS traffic
PostgreSQL (proxy + replication)
Patroni → etcd (leader election)
LDAP + Data Grid cross-site
Coupled health check

HAProxy performs a two-step health check: it verifies the Patroni leader status (/primary) and the Keycloak health (/realms/master). HTTP traffic is only routed to the site whose PostgreSQL is the active primary — ensuring that Keycloak and its database are always on the same site. When the leader changes (failover or switchover), all traffic moves together.

Testing Guide

Test credentials: any LDAP user (e.g. aragorn, gandalf) with password Test123

Status Bar

FieldMeaning
ACTIVE SITEWhich Keycloak site is currently serving HTTP traffic
SITE-A / SITE-BUP or DOWN based on direct health check to each Keycloak

Footer

FieldMeaning
ServingWhich Keycloak site served the last polled request
Auth statusAuthenticated (green) or Not Authenticated (red)

Keycloak Pods (Stop / Start)

Scales Keycloak pods to 0 or 1 on each site.

Test: Keycloak Failover

  1. Login with aragorn / Test123.
  2. Click Stop on Site-A Keycloak.
  3. Wait ~10s. The watchdog detects the failure (~4s) and triggers a Patroni switchover. pg-b becomes Leader. ACTIVE SITE switches to keycloak-b. Footer shows Serving: keycloak-b.
  4. Click Refresh Token. Token refreshes successfully (session survived via Data Grid cross-site replication).
  5. Click Start on Site-A Keycloak. Then click Switchover on Patroni to return pg-a to Leader. Traffic returns to keycloak-a.

Data Grid Pods (Stop / Start)

Scales Data Grid (Infinispan) pods to 0 or 1 on each site.

Test: Data Grid Failure Impact

  1. Login with aragorn / Test123.
  2. Click Stop on Site-A Data Grid.
  3. Click Stop on Site-A Keycloak, then Start again. Keycloak restarts without external cache.
  4. Restart Data Grid with Start to restore cross-site replication.

Cache Mode

Switches Keycloak between external Data Grid cache and local embedded cache.

ModeBehavior
External (Data Grid)Full HA with cross-site session replication. Failover preserves sessions.
LocalEach Keycloak uses its own embedded cache. No cross-site replication. Failover loses sessions.

Test: Session Persistence Difference

  1. Set cache to External. Login. Stop Site-A Keycloak. Session survives.
  2. Set cache to Local. Login. Stop Site-A Keycloak. Session is lost (re-authentication required).

Sessions & Users

ButtonAction
ListShows all active sessions in realm middleearth
Kill My SessionTerminates your current session. You will be logged out after 2 seconds.

PostgreSQL HA (Patroni)

Shows the Patroni cluster status in real-time.

BadgeMeaning
LeaderThis node is the PostgreSQL primary (accepts writes)
ReplicaThis node is a streaming replica (read-only)
StoppedPatroni service is not running on this node
ButtonAction
StopStops Patroni service on the node (simulates failure)
StartStarts Patroni service on the node
SwitchoverPromotes the replica to leader (planned switchover)

Test: PostgreSQL Switchover

  1. Verify pg-a is Leader, pg-b is Replica.
  2. Click Switchover.
  3. pg-b becomes Leader. pg-a becomes Replica.
  4. ACTIVE SITE switches to keycloak-b (HTTP traffic follows the database leader).
  5. Footer updates to Serving: keycloak-b.
  6. Click Switchover again to return to pg-a.

Test: PostgreSQL Failure (Automatic Failover)

  1. Verify pg-a is Leader.
  2. Click Stop on pg-a.
  3. pg-a shows Stopped. Patroni promotes pg-b to Leader automatically (~10s).
  4. ACTIVE SITE switches to keycloak-b.
  5. Click Start on pg-a. It rejoins as Replica.

Test: Coupled HTTP + Database Routing

  1. Login with aragorn / Test123.
  2. Note: ACTIVE SITE = keycloak-a, Leader = pg-a, Serving = keycloak-a.
  3. Click Switchover on Patroni.
  4. All three change together: ACTIVE SITE = keycloak-b, Leader = pg-b, Serving = keycloak-b.
  5. Click Refresh Token. It works (Keycloak-B connects to pg-b via HAProxy).

JWT Viewer (after login)

SectionContent
Token toolbarExpiry countdown, email, username, refresh count
Encoded TokenRaw JWT with color-coded header / payload / signature
Access Token tabDecoded header + payload (roles, scope, session ID)
ID Token tabDecoded header + payload (user profile, email)
CopyCopies the raw access token to clipboard
Refresh TokenForces token refresh (grant_type=refresh_token)