private Mono<List<Group>> search(
            @Nullable Integer skip,
            @Nullable Integer limit,
            @Nullable Set<Long> groupIds,
            @NotNull String name,
            @Nullable List<Integer> fieldsToHighlight) {
        if (!elasticsearchManager.isGroupUseCaseEnabled()) {
            return Mono
                    .error(ResponseException.get(ResponseStatusCode.SEARCHING_GROUP_IS_DISABLED));
        }
        boolean highlight = CollectionUtil.isNotEmpty(fieldsToHighlight);
        return elasticsearchManager
                .searchGroupDocs(skip, limit, name, groupIds, highlight, null, null)
                .flatMap(response -> {
                    List<Hit<GroupDoc>> hits = response.hits()
                            .hits();
                    int count = hits.size();
                    if (count == 0) {
                        return PublisherPool.emptyList();
                    }
                    if (highlight) {
                        Map<Long, String> groupIdToHighlightedName =
                                CollectionUtil.newMapWithExpectedSize(count);
                        List<Long> ids = new ArrayList<>(count);
                        for (Hit<GroupDoc> hit : hits) {
                            Long id = Long.parseLong(hit.id());
                            Collection<List<String>> highlightValues = hit.highlight()
                                    .values();
                            if (!highlightValues.isEmpty()) {
                                List<String> values = highlightValues.iterator()
                                        .next();
                                if (!values.isEmpty()) {
                                    groupIdToHighlightedName.put(id, values.getFirst());
                                }
                            }
                            ids.add(id);
                        }
                        Mono<List<Group>> mono = groupRepository.findNotDeletedGroups(ids, null)
                                .collect(CollectorUtil.toList(count));
                        return mono.map(groups -> {
                            if (groups.isEmpty()) {
                                return Collections.emptyList();
                            }
                            Map<Long, Group> groupIdToGroup =
                                    CollectionUtil.newMapWithExpectedSize(groups.size());
                            for (Group group : groups) {
                                groupIdToGroup.put(group.getId(), group);
                            }
                            for (Map.Entry<Long, String> entry : groupIdToHighlightedName
                                    .entrySet()) {
                                Group group = groupIdToGroup.get(entry.getKey());
                                if (group != null) {
                                    group.setName(entry.getValue());
                                }
                            }
                            return groups;
                        });
                    } else {
                        List<Long> ids = new ArrayList<>(count);
                        for (Hit<GroupDoc> hit : hits) {
                            ids.add(Long.parseLong(hit.id()));
                        }
                        return groupRepository.findNotDeletedGroups(ids, null)
                                .collect(CollectorUtil.toList(count));
                    }
                });
    }
@implNote We don't need to check if the group count with the specified type owned by the
          requester exceeds here because it is implemented in
          {@link GroupService#isAllowedToCreateGroup}
turms-service/src/main/java/im/turms/service/domain/group/service/GroupService.java