From f1532565b6f6a1a670c8aee591c9f5b43324f1ab Mon Sep 17 00:00:00 2001 From: Stefan Guilhen Date: Fri, 19 Apr 2024 15:20:19 -0300 Subject: [PATCH] Don't use no-arg version of GroupModel.getSubGroupsStream() when fetching the subgroups from the GroupResource endpoint. - prevents pre-loading all groups; instead use the stream from the JPA adapter to load subgroups one by one and then filter based on the user permissions. Closes #28935 Signed-off-by: Stefan Guilhen --- .../main/java/org/keycloak/models/jpa/GroupAdapter.java | 1 - .../keycloak/services/resources/admin/GroupResource.java | 8 ++++---- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/model/jpa/src/main/java/org/keycloak/models/jpa/GroupAdapter.java b/model/jpa/src/main/java/org/keycloak/models/jpa/GroupAdapter.java index ff7e370e53..988fbefb22 100755 --- a/model/jpa/src/main/java/org/keycloak/models/jpa/GroupAdapter.java +++ b/model/jpa/src/main/java/org/keycloak/models/jpa/GroupAdapter.java @@ -144,7 +144,6 @@ public class GroupAdapter implements GroupModel , JpaModel { .map(realm::getGroupById) // In concurrent tests, the group might be deleted in another thread, therefore, skip those null values. .filter(Objects::nonNull) - .sorted(GroupModel.COMPARE_BY_NAME) ); } diff --git a/services/src/main/java/org/keycloak/services/resources/admin/GroupResource.java b/services/src/main/java/org/keycloak/services/resources/admin/GroupResource.java index b3471464bb..ecee44b292 100755 --- a/services/src/main/java/org/keycloak/services/resources/admin/GroupResource.java +++ b/services/src/main/java/org/keycloak/services/resources/admin/GroupResource.java @@ -164,10 +164,10 @@ public class GroupResource { @QueryParam("briefRepresentation") @DefaultValue("false") Boolean briefRepresentation) { this.auth.groups().requireView(group); boolean canViewGlobal = auth.groups().canView(); - return paginatedStream( - group.getSubGroupsStream() - .filter(g -> canViewGlobal || auth.groups().canView(g)), first, max) - .map(g -> GroupUtils.populateSubGroupCount(g, GroupUtils.toRepresentation(auth.groups(), g, !briefRepresentation))); + return paginatedStream(group.getSubGroupsStream(-1, -1) + .filter(g -> canViewGlobal || auth.groups().canView(g)) + .map(g -> GroupUtils.populateSubGroupCount(g, GroupUtils.toRepresentation(auth.groups(), g, !briefRepresentation))) + , first, max); } /**