I’m using Keycloak 25 with a custom user storage provider:
CustomerStorageProvider implements
UserStorageProvider,
UserLookupProvider,
CredentialInputValidator,
CredentialInputUpdater
In this provider, getUserById and getUserByUsername call an external API to look up users by username.
What I want to achieve
I need different lookup logic when the user logs in via an Identity Provider (IdP):
For normal login → lookup by username (current behavior)
For IdP login → call a different API using a claim from the IdP
userinforesponse (instead of username)
What I tried
I added a custom step in a custom authentication flow, attached to the First Broker Login Flow of my IdP.
In this step, I successfully call the alternative API using a claim from the IdP.
This works fine on the first login, because no federated user exists yet:
UserModel federatedUser = session.users()
.getUserByFederatedIdentity(realmModel, federatedIdentityModel);
inside IdentityBrokerService returns null, so the First Broker Login flow is executed.
The problem
After the first login:
The federated user is stored in Keycloak
The
storageIdpoints to myCustomerStorageProviderOn subsequent logins, Keycloak resolves the user via my provider
This triggers
getUserById/getUserByUsername, which again call the API using username
However, I still want to use the IdP claim-based lookup, not the username-based one.
Question
How can I:
Detect that the login is happening via an Identity Provider (after the first login), and
Override or bypass the default
UserStorageProviderlookup so I can call my external API using IdP claims instead of username?
Is there a recommended extension point (e.g., broker flow, mapper, or SPI) to handle this scenario properly?