KEYCLOAK-9002 StackOverflowError when reading LDAP-backed users via REST API
This commit is contained in:
parent
3462be857b
commit
88141320ac
2 changed files with 39 additions and 0 deletions
|
@ -39,6 +39,7 @@ import org.keycloak.credential.CredentialModel;
|
||||||
import org.keycloak.federation.kerberos.impl.KerberosUsernamePasswordAuthenticator;
|
import org.keycloak.federation.kerberos.impl.KerberosUsernamePasswordAuthenticator;
|
||||||
import org.keycloak.federation.kerberos.impl.SPNEGOAuthenticator;
|
import org.keycloak.federation.kerberos.impl.SPNEGOAuthenticator;
|
||||||
import org.keycloak.models.*;
|
import org.keycloak.models.*;
|
||||||
|
import org.keycloak.models.cache.CachedUserModel;
|
||||||
import org.keycloak.models.utils.DefaultRoles;
|
import org.keycloak.models.utils.DefaultRoles;
|
||||||
import org.keycloak.models.utils.ReadOnlyUserModelDelegate;
|
import org.keycloak.models.utils.ReadOnlyUserModelDelegate;
|
||||||
import org.keycloak.policy.PasswordPolicyManagerProvider;
|
import org.keycloak.policy.PasswordPolicyManagerProvider;
|
||||||
|
@ -160,6 +161,16 @@ public class LDAPStorageProvider implements UserStorageProvider,
|
||||||
return existing;
|
return existing;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// We need to avoid having CachedUserModel as cache is upper-layer then LDAP. Hence having CachedUserModel here may cause StackOverflowError
|
||||||
|
if (local instanceof CachedUserModel) {
|
||||||
|
local = session.userStorageManager().getUserById(local.getId(), realm);
|
||||||
|
|
||||||
|
existing = userManager.getManagedProxiedUser(local.getId());
|
||||||
|
if (existing != null) {
|
||||||
|
return existing;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
UserModel proxied = local;
|
UserModel proxied = local;
|
||||||
|
|
||||||
checkDNChanged(realm, local, ldapObject);
|
checkDNChanged(realm, local, ldapObject);
|
||||||
|
|
|
@ -985,6 +985,34 @@ public class LDAPProvidersIntegrationTest extends AbstractLDAPTest {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// KEYCLOAK-9002
|
||||||
|
@Test
|
||||||
|
public void testSearchWithPartiallyCachedUser() {
|
||||||
|
testingClient.server().run(session -> {
|
||||||
|
session.userCache().clear();
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
// This will load user from LDAP and partially cache him (including attributes)
|
||||||
|
testingClient.server().run(session -> {
|
||||||
|
LDAPTestContext ctx = LDAPTestContext.init(session);
|
||||||
|
RealmModel appRealm = ctx.getRealm();
|
||||||
|
UserModel user = session.users().getUserByUsername("johnkeycloak", appRealm);
|
||||||
|
Assert.assertNotNull(user);
|
||||||
|
|
||||||
|
user.getAttributes();
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
// Assert search without arguments won't blow up with StackOverflowError
|
||||||
|
adminClient.realm("test").users().search(null, 0, 10, false);
|
||||||
|
|
||||||
|
List<UserRepresentation> users = adminClient.realm("test").users().search("johnkeycloak", 0, 10, false);
|
||||||
|
Assert.assertTrue(users.stream().anyMatch(userRepresentation -> "johnkeycloak".equals(userRepresentation.getUsername())));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testLDAPUserRefreshCache() {
|
public void testLDAPUserRefreshCache() {
|
||||||
testingClient.server().run(session -> {
|
testingClient.server().run(session -> {
|
||||||
|
|
Loading…
Reference in a new issue