Join our Newsletter — 33% off our NHI Course
Home› Guides› Keycloak Hardening Guide: Realms, Clients and Production Deployment
Guide Identity & Access Management (IAM)

Keycloak Hardening Guide: Realms, Clients and Production Deployment

PDF for newsletter subscribers · free to read online

← All guides
By NHI Mgmt Group, edited by Lalit Choda Updated 26 October 2026 15 min read
On this page

A default Keycloak installation is built to be easy to start, not safe to expose, and many production deployments still carry development habits: a busy master realm, an internet-facing admin console and confidential clients with unrotated secrets. Because Keycloak issues the tokens that every connected application trusts, a weak realm or client setting becomes a weakness in all of them. This guide covers the Keycloak 26.x server and its realms, clients, admin roles, service accounts, events and network exposure, using the option and setting names from the official keycloak.org documentation. It is written for IAM engineers, platform teams and security architects who run Keycloak themselves, whether on virtual machines, containers or the Keycloak Operator on Kubernetes. If you also run PingOne or PingFederate, our Ping Identity security hardening guide covers the equivalent controls.

Key takeaways

  • Keep the master realm for administration only. Create a separate realm for each user population and do not place ordinary users or applications in master, because master admins can manage every realm on the server.
  • Never expose the admin console or Admin REST API to the internet. Use a separate admin hostname, block /admin/ at the reverse proxy and keep the management interface on port 9000 internal.
  • Treat every confidential client and service account as a non-human identity. Prefer Signed JWT or certificate client authentication, rotate secrets with the secret rotation client policy and scope service account roles tightly.
  • Turn on the defences that are off by default. Brute force detection is disabled and login and admin events are not stored until you enable them per realm.
  • Shorten token and session lifetimes and plan revocation. Short access tokens, revoked refresh tokens and a tested not-before push limit what a stolen token is worth.

How identity and access work in Keycloak

Keycloak is an open source identity and access management server that speaks OpenID Connect, OAuth 2.0 and SAML 2.0. Its security model rests on a few objects, and most hardening decisions are about one of them.

ObjectWhat it isSecurity relevance
RealmAn isolated namespace of users, clients, roles, keys and policiesThe trust boundary. Signing keys, session settings, brute force detection and events are configured per realm.
Master realmThe realm created at first start that holds server administratorsAdmins here can create and manage every realm. Keycloak documentation advises using it only to manage other realms.
ClientAn application or service that requests tokens (OIDC) or assertions (SAML)Public clients (browser, mobile) cannot keep a secret; confidential clients authenticate with a secret, Signed JWT or certificate.
Service accountA user automatically linked to a confidential client for the client credentials grantA machine identity whose roles are often over-granted and rarely reviewed.
Roles and client scopesRealm roles, client roles and scopes that decide which claims reach a tokenRole scope mappings are unlimited by default, so tokens can carry far more roles than the client needs.
Identity providers and user federationExternal IdPs (OIDC, SAML, social) and LDAP or Active Directory federationHold bind credentials and client secrets that belong in a vault, and import trust from outside the realm.

Flows tie these together: an authentication flow decides which authenticators (password, OTP, WebAuthn) a user passes, and client policies can enforce rules such as allowed redirect URIs or client authentication methods for every client in a realm. For the protocol background see the OAuth 2.0 and OpenID Connect Guide, and for IdP-wide controls see the Identity Provider and SSO Security Guide.

Admin roles and privileged access

Keycloak has two layers of administration. In the master realm, the global admin role grants full control of the server and create-realm lets a user create new realms. Each realm also appears in master as a client named <realm>-realm, whose roles grant administration of that realm from master. Inside each realm, the realm-management client carries fine-grained roles.

realm-management roleWhat it allowsHardening note
realm-adminEvery administrative action in that realmEquivalent to realm owner. Assign to very few named people, never to service accounts used by applications.
manage-usersCreate, edit and delete users, set credentials, assign roles the admin already holdsKeycloak only lets this role assign roles the admin holds, but combined with broad roles it is still a privilege escalation path.
impersonationLog in as another userHighly sensitive. Remove from all accounts that do not need support impersonation and alert on its use.
manage-clientsCreate and change clients, view client secretsViewing a confidential client secret requires this role, so it is effectively secret read access.
manage-realm, manage-identity-providers, manage-eventsRealm settings, external IdPs, event configurationAn attacker with these can add a rogue IdP or switch off event storage.
view-users, view-clients, view-events, query-*Read-only accessUse for support and audit roles instead of manage roles.
  • Delegated administration: Fine-grained admin permissions (version 2, enabled with the Admin Permissions realm setting) let you grant admins rights over specific users, groups, clients, roles or organisations through the admin-permissions client. Users holding admin or realm-admin are not affected, so the feature narrows delegated admins, not super admins.
  • Admin roles from tokens are ignored: admin roles added through protocol mappers do not grant console rights, so privilege must be assigned explicitly and can be reviewed in role mappings.
  • Bootstrap admin: the first admin created with KC_BOOTSTRAP_ADMIN_USERNAME and KC_BOOTSTRAP_ADMIN_PASSWORD (default username temp-admin) is temporary. Create named, MFA-protected admins, then delete it. The bootstrap-admin command creates a recovery admin or service account if all admins are lost; restrict who can run it, because it needs host access to the server.
  • MFA for admins: require OTP or WebAuthn for the master realm browser flow, or federate master to your workforce IdP with phishing-resistant MFA. See the Phishing-Resistant MFA Guide.
  • Break-glass: keep one local master realm admin with a hardware key and a sealed password for when federation fails. See the Break-Glass Account Guide.

Integrations, API tokens and service accounts

Most Keycloak compromise paths that do not start with a user password start with a client credential. Confidential clients, service accounts, federation bind accounts and identity provider secrets are all non-human identities and need the same lifecycle as any other secret.

Client authentication optionHow it worksWhen to choose it
Client Id and Secret (default)Shared secret sent to the token endpointAcceptable for low-risk internal services if rotated and stored in a vault. Weakest option: anyone who reads the secret can be the client.
Signed JWTClient signs an assertion with its private key; Keycloak verifies with a registered key or a JWKS URLPreferred for services that can hold a key. No shared secret is stored in Keycloak, and a JWKS URL lets the client rotate keys itself.
Signed JWT with client secretAssertion signed with HMAC using the secretOnly where the client cannot hold an asymmetric key; it still depends on a shared secret.
X509 certificate (mutual TLS)Client proves possession of a certificate at the TLS layerHigh-assurance and FAPI-style deployments; also enables certificate-bound tokens so a stolen token cannot be replayed without the key.
  • Secret rotation: the secret rotation client policy lets a client keep two active secrets during a rotation window, so you can rotate without an outage. Set an expiry and rotate on a schedule and after any staff change on the owning team.
  • Service accounts: enable Service accounts roles only on clients that use the client credentials grant, and assign only the client roles needed. The Full Scope Allowed setting puts every role the account holds into its tokens; switch it off and map explicit role scopes. Never give an application service account realm-admin or manage-users unless it is a provisioning tool, and then document it. See the Machine-to-Machine OAuth (Client Credentials) Guide.
  • Admin REST API automation: Terraform providers, CI pipelines and provisioning scripts usually authenticate as a service account in master or the target realm. Give them per-realm roles rather than the global admin role, restrict their network origin at the proxy and log their admin events.
  • Vault for server-side secrets: SMTP passwords, LDAP bind credentials and identity provider client secrets can be referenced from the file-based or PKCS12 keystore vault (${vault.key}) instead of being stored in the database. See the Secrets Management Guide.
  • Redirect URIs and public clients: exact redirect URIs (no wildcards), PKCE for public clients and the secure redirect URIs enforcer client policy executor close the most common authorisation code theft paths.
  • Offline tokens: remove the offline_access scope from clients that do not need long-lived refresh tokens, and set Offline Session Max Limited for those that do.

The OneLogin incident shows why secrets held by an IdP matter: the OneLogin API flaw exposed OIDC client secrets to anyone holding an API key, which is the same class of exposure as an over-granted manage-clients or view-clients role in Keycloak.

Logging and detection

Keycloak does not store events by default: only errors reach the server log. Enable storage per realm under Realm settings, Events.

  • User events: turn on Save events with an Expiration that matches your retention policy, and forward them to the SIEM. The jboss-logging event listener writes events to the org.keycloak.events log category, which is the simplest route to a log pipeline.
  • Admin events: enable admin events and Include representation so you can see what was changed, not just that something changed. Long representations can be truncated; tune --spi-events-store--jpa--max-field-length if you store them in the database.
  • Health and metrics: /health and /metrics are served on the management interface (port 9000). Scrape them internally; never route them through the public proxy.
SignalEvent or sourceWhat it can indicate
Bursts of LOGIN_ERROR with invalid_user_credentials across many usernamesUser eventsPassword spraying or credential stuffing (ATT&CK T1110)
Brute force lockout events for privileged usersUser eventsTargeted guessing against admins
CLIENT_LOGIN from a service account at unusual times or from new IP rangesUser events plus proxy logsStolen client secret in use (T1528, T1550.001)
Admin events creating clients, identity providers or role mappings, or changing authentication flowsAdmin eventsPersistence or MFA weakening (T1098, T1556.006)
IMPERSONATE eventsUser eventsUse of the impersonation role; should be rare and ticketed
Requests to /admin/ paths at the public proxyReverse proxy or WAF logsExposure mistake or reconnaissance

Metrics to track: percentage of realms with events and admin events stored; number of confidential clients still using Client Id and Secret; median age of client secrets; number of accounts holding realm-admin, admin or impersonation; percentage of master realm admins with MFA; and time from Keycloak security release to production upgrade. See the SIEM Guide for building the detections.

Hardening baseline

Server and network

  • TLS everywhere: run with HTTPS (https-certificate-file and https-certificate-key-file, or terminate at the proxy and re-encrypt) and leave HTTP disabled. Set each realm's Require SSL to all requests; the default, external requests, allows plain HTTP from private IP addresses.
  • Hostname: the hostname option is mandatory in production. Do not set hostname-strict=false on an exposed server, because Keycloak would then derive URLs from request headers. Set hostname-admin to an internal hostname; note that it moves the console but does not block the Admin REST API, so the proxy must do that.
  • Reverse proxy: set proxy-headers to forwarded or xforwarded to match your proxy and proxy-trusted-addresses to the proxy's addresses so spoofed headers from elsewhere are ignored.
PathExpose publicly?Reason
/realms/YesOIDC and SAML endpoints used by applications and users
/resources/YesStatic assets for login pages
/.well-known/YesDiscovery metadata
/realms/master/NoToken endpoint for admin logins; keep internal
/admin/NoAdmin console and Admin REST API
/metrics, /healthNoServed on the management interface, port 9000
  • Load and availability: set http-max-queued-requests to shed load instead of exhausting memory, run at least two instances against a production database, and use /health/ready for load balancer checks. Cluster traffic between nodes (JGroups) is encrypted with TLS by default in current releases; do not disable it.
  • Patching: follow Keycloak security advisories and keep to a supported 26.x minor release. Upgrades are also how you inherit changed defaults.

Realm settings

SettingDefaultHardened value
Brute Force Detection (Security Defenses)DisabledEnabled; review Max Login Failures (30 when enabled), Wait Increment (1 min), Max Wait (15 min) and Failure Reset Time (12 h). Lower Max Login Failures for most workforce realms. Applies to passwords, OTP and recovery codes.
Require SSLexternal requestsall requests
Events and admin eventsNot storedStored with expiry and forwarded to SIEM
Role scope mappings on clientsFull scope (unlimited)Full Scope Allowed off; explicit scopes per client
Realm keysGenerated at realm creationRotate every three to six months, keeping the old key passive until issued tokens expire
Revoke Refresh TokenOffOn, so each refresh token is single-use and replay is detectable
SSO Session Idle and Max, Access Token LifespanProduct defaultsSet from your session policy; keep access tokens in minutes, not hours

For lifetime design see the Token Lifetime Policy Design Guide, and for lockout tuning the Account Lockout and Brute-Force Protection Guide.

Rollout order

  1. Inventory: list realms, clients (public or confidential, authentication method, secret age), service accounts and their roles, every holder of admin, realm-admin and impersonation, and every identity provider and federation link.
  2. Close exposure first: block /admin/, /realms/master/ and port 9000 at the proxy, set hostname, hostname-admin and trusted proxy addresses. Test admin access over the internal path before cutting the public one, and keep the old rule ready to restore.
  3. Turn on visibility: enable events and admin events in every realm and confirm they arrive in the SIEM before changing anything else, so later changes are recorded.
  4. Secure admins: named admins with MFA, delete the temporary bootstrap admin, remove unused admin and impersonation roles, set up the break-glass account.
  5. Pilot client changes: on a staging realm export, move one confidential client to Signed JWT, switch off Full Scope Allowed and shorten token lifespans. Watch for CODE_TO_TOKEN_ERROR and CLIENT_LOGIN_ERROR events; roll back by restoring the client settings from the realm export.
  6. Enable brute force detection and client policies realm by realm, starting with the workforce realm, then customer realms where lockout affects support volume.
  7. Make it repeatable: keep realm configuration in code (realm import or a declarative tool), review it in pull requests and schedule key and secret rotation.

Small vs large estates: a single team with one or two realms can rely on a hardened master realm with named admins and MFA. Large or multi-tenant deployments should use fine-grained admin permissions or separate Keycloak clusters per tenant group, because a master realm admin compromise affects every realm on the cluster.

Common misconfigurations

  • Admin console on the public hostname. The console and Admin REST API are reachable wherever /admin/ is routed. Setting hostname-admin alone does not stop API calls on the public host.
  • Applications and users in the master realm. It makes every application user a neighbour of the server admins and puts application flows next to the realm that controls everything.
  • Brute force detection never switched on. It is off by default, so password spraying against a customer realm is only limited by your proxy. The Taiwan government SSO incident shows how automated password spraying of predictable passwords leads straight into SSO-connected systems.
  • Long-lived client secrets with broad service account roles. A secret copied into a CI variable years ago, attached to a service account with manage-users, is an administrator credential that never expires.
  • Wildcard redirect URIs and public clients without PKCE. These allow authorisation codes and tokens to be sent to attacker-controlled locations.
  • No event storage. When an incident happens there is no record of which admin changed a flow or which client minted tokens, and investigation relies on proxy logs alone.

Framework mapping

Control areaNIST SP 800-53 Rev. 5NIST CSF 2.0CIS Controls v8.1ISO/IEC 27001:2022 Annex A
Admin roles, least privilege, service accountsAC-2, AC-6PR.AA-05Control 5, Control 6A.5.15, A.8.2
Admin MFA, client authenticationIA-2, IA-2(1), IA-5PR.AA-01, PR.AA-03Control 6A.5.17, A.8.5
TLS, hostname, proxy and secure configurationSC-8, CM-6PR.PS-01Control 4A.8.9
Events, admin events and monitoringAU-2, AU-6PR.PS-04, DE.CM-03Control 8A.8.15, A.8.16

Practitioner checklist

  • Block /admin/, /realms/master/, /metrics and /health at the public proxy and serve the console on an internal hostname-admin.
  • Set hostname, proxy-headers and proxy-trusted-addresses; never run hostname-strict=false in production.
  • Set Require SSL to all requests in every realm.
  • Remove applications and ordinary users from the master realm; use named, MFA-protected admins and delete the temporary bootstrap admin.
  • Review every holder of admin, realm-admin, manage-users, manage-clients and impersonation quarterly.
  • Move confidential clients to Signed JWT or mutual TLS where possible; rotate remaining secrets with the secret rotation policy.
  • Switch off Full Scope Allowed and scope service account roles to what each integration needs.
  • Enable brute force detection, Revoke Refresh Token and short access token lifespans in each realm.
  • Enable user and admin event storage with representations and forward events to the SIEM.
  • Rotate realm signing keys every three to six months and keep realm configuration in version control.

Standards and references

Related NHI Mgmt Group resources: Identity Provider and SSO Security Guide · OAuth 2.0 and OpenID Connect Guide · Machine-to-Machine OAuth (Client Credentials) Guide · Service Account Security Guide · Duo Hardening Guide

PDF for subscribers

Take this guide with you

Every section, table and checklist in one PDF, with links to the sources and related guides. Subscribe to our weekly NHI & AI Identity Journal and we’ll email you a download link.

Free weekly newsletter

Subscribe to the NHI & AI Identity Journal

The latest on NHI and Agentic AI security – articles, research, breaches, news and events every week.

Bonus 33% off our NHI Course when you subscribe.

NHIMG Editorial Note
Researched and written by the NHI Mgmt Group editorial team using AI tools, under the editorial direction of Lalit Choda. Facts are drawn from the sources listed on this page and checked by our automated quality process. Last updated 26 October 2026. Spotted an error? Use our contact page.
NHI Mgmt Group, the independent authority on Non-Human Identity, IAM and Agentic AI security. nhimg.org

PDF Downloads for Newsletter Subscribers

Get the guide

Enter your details and we’ll email you a download link.

The full guide is free to read online. The PDF is a thank you for subscribing.

Fill in all fields marked * and tick the PDF box to continue.