github.com/weaviate/weaviate@v1.24.6/test/acceptance/graphql_resolvers/local_aggregate_matrix_groupby_test.go (about)

     1  //                           _       _
     2  // __      _____  __ ___   ___  __ _| |_ ___
     3  // \ \ /\ / / _ \/ _` \ \ / / |/ _` | __/ _ \
     4  //  \ V  V /  __/ (_| |\ V /| | (_| | ||  __/
     5  //   \_/\_/ \___|\__,_| \_/ |_|\__,_|\__\___|
     6  //
     7  //  Copyright © 2016 - 2024 Weaviate B.V. All rights reserved.
     8  //
     9  //  CONTACT: hello@weaviate.io
    10  //
    11  
    12  package test
    13  
    14  import (
    15  	"fmt"
    16  	"testing"
    17  
    18  	"github.com/stretchr/testify/assert"
    19  	"github.com/stretchr/testify/require"
    20  	"github.com/weaviate/weaviate/test/helper"
    21  	graphqlhelper "github.com/weaviate/weaviate/test/helper/graphql"
    22  )
    23  
    24  func aggregateArrayClassWithGroupByTest(t *testing.T) {
    25  	asserts := newAggregateResponseAssert(t)
    26  	testCasesGen := &aggregateArrayClassTestCases{}
    27  
    28  	t.Run("aggregate ArrayClass with group by texts", func(t *testing.T) {
    29  		expectedAllResultsAssertions := map[string][]assertFunc{
    30  			"Alpha": {
    31  				asserts.groupedBy("Alpha", "texts"),
    32  				asserts.meta(4),
    33  				asserts.booleanArray("booleans", 10, 4, 6, 0.4, 0.6),
    34  				asserts.textArray("texts", 10, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{4, 3, 2, 1}),
    35  				asserts.numberArray("numbers", 10, 4, 1, 1, 20, 2, 2),
    36  				asserts.intArray("ints", 10, 104, 101, 101, 1020, 102, 102),
    37  				asserts.dateArray("dates", 10),
    38  			},
    39  			"Bravo": {
    40  				asserts.groupedBy("Bravo", "texts"),
    41  				asserts.meta(3),
    42  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
    43  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{3, 3, 2, 1}),
    44  				asserts.numberArray("numbers", 9, 4, 1, 1, 19, 2, 2.111111111111111),
    45  				asserts.intArray("ints", 9, 104, 101, 101, 919, 102, 102.11111111111111),
    46  				asserts.dateArray("dates", 9),
    47  			},
    48  			"Charlie": {
    49  				asserts.groupedBy("Charlie", "texts"),
    50  				asserts.meta(2),
    51  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
    52  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
    53  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
    54  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
    55  				asserts.dateArray("dates", 7),
    56  			},
    57  			"Delta": {
    58  				asserts.groupedBy("Delta", "texts"),
    59  				asserts.meta(1),
    60  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
    61  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{1, 1, 1, 1}),
    62  				asserts.numberArray("numbers", 4, 4, 1, 1, 10, 2.5, 2.5),
    63  				asserts.intArray("ints", 4, 104, 101, 101, 410, 102.5, 102.5),
    64  				asserts.dateArray("dates", 4),
    65  			},
    66  		}
    67  		expectedResultsWithDataAssertions := map[string][]assertFunc{
    68  			"Alpha": {
    69  				asserts.groupedBy("Alpha", "texts"),
    70  				asserts.meta(2),
    71  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
    72  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
    73  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
    74  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
    75  				asserts.dateArray("dates", 7),
    76  			},
    77  			"Bravo": {
    78  				asserts.groupedBy("Bravo", "texts"),
    79  				asserts.meta(2),
    80  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
    81  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
    82  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
    83  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
    84  				asserts.dateArray("dates", 7),
    85  			},
    86  			"Charlie": {
    87  				asserts.groupedBy("Charlie", "texts"),
    88  				asserts.meta(2),
    89  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
    90  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
    91  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
    92  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
    93  				asserts.dateArray("dates", 7),
    94  			},
    95  			"Delta": {
    96  				asserts.groupedBy("Delta", "texts"),
    97  				asserts.meta(1),
    98  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
    99  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{1, 1, 1, 1}),
   100  				asserts.numberArray("numbers", 4, 4, 1, 1, 10, 2.5, 2.5),
   101  				asserts.intArray("ints", 4, 104, 101, 101, 410, 102.5, 102.5),
   102  				asserts.dateArray("dates", 4),
   103  			},
   104  		}
   105  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
   106  		expectedNoResultsAssertions := map[string][]assertFunc{}
   107  
   108  		testCases := []aggregateTestCase{
   109  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   110  
   111  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   112  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
   113  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   114  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
   115  
   116  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
   117  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
   118  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   119  
   120  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
   121  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
   122  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   123  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
   124  		}
   125  
   126  		for _, tc := range testCases {
   127  			query := aggregateArrayClassQuery(tc.filters, "groupBy: [\"texts\"]")
   128  
   129  			t.Run(tc.name, func(t *testing.T) {
   130  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   131  				extracted := extractArrayClassGroupByResult(result)
   132  
   133  				assert.Len(t, extracted, len(tc.groupedAssertions))
   134  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   135  					group := findGroup(groupedBy, extracted)
   136  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   137  
   138  					for _, assertion := range groupAssertions {
   139  						assertion(group)
   140  					}
   141  				}
   142  			})
   143  		}
   144  	})
   145  
   146  	t.Run("aggregate ArrayClass with group by ints", func(t *testing.T) {
   147  		expectedAllResultsAssertions := map[string][]assertFunc{
   148  			"101": {
   149  				asserts.groupedBy("101", "ints"),
   150  				asserts.meta(4),
   151  				asserts.booleanArray("booleans", 10, 4, 6, 0.4, 0.6),
   152  				asserts.textArray("texts", 10, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{4, 3, 2, 1}),
   153  				asserts.numberArray("numbers", 10, 4, 1, 1, 20, 2, 2),
   154  				asserts.intArray("ints", 10, 104, 101, 101, 1020, 102, 102),
   155  				asserts.dateArray("dates", 10),
   156  			},
   157  			"102": {
   158  				asserts.groupedBy("102", "ints"),
   159  				asserts.meta(3),
   160  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   161  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{3, 3, 2, 1}),
   162  				asserts.numberArray("numbers", 9, 4, 1, 1, 19, 2, 2.111111111111111),
   163  				asserts.intArray("ints", 9, 104, 101, 101, 919, 102, 102.11111111111111),
   164  				asserts.dateArray("dates", 9),
   165  			},
   166  			"103": {
   167  				asserts.groupedBy("103", "ints"),
   168  				asserts.meta(2),
   169  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   170  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   171  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   172  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   173  				asserts.dateArray("dates", 7),
   174  			},
   175  			"104": {
   176  				asserts.groupedBy("104", "ints"),
   177  				asserts.meta(1),
   178  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   179  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{1, 1, 1, 1}),
   180  				asserts.numberArray("numbers", 4, 4, 1, 1, 10, 2.5, 2.5),
   181  				asserts.intArray("ints", 4, 104, 101, 101, 410, 102.5, 102.5),
   182  				asserts.dateArray("dates", 4),
   183  			},
   184  		}
   185  		expectedResultsWithDataAssertions := map[string][]assertFunc{
   186  			"101": {
   187  				asserts.groupedBy("101", "ints"),
   188  				asserts.meta(2),
   189  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   190  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   191  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   192  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   193  				asserts.dateArray("dates", 7),
   194  			},
   195  			"102": {
   196  				asserts.groupedBy("102", "ints"),
   197  				asserts.meta(2),
   198  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   199  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   200  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   201  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   202  				asserts.dateArray("dates", 7),
   203  			},
   204  			"103": {
   205  				asserts.groupedBy("103", "ints"),
   206  				asserts.meta(2),
   207  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   208  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   209  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   210  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   211  				asserts.dateArray("dates", 7),
   212  			},
   213  			"104": {
   214  				asserts.groupedBy("104", "ints"),
   215  				asserts.meta(1),
   216  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   217  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{1, 1, 1, 1}),
   218  				asserts.numberArray("numbers", 4, 4, 1, 1, 10, 2.5, 2.5),
   219  				asserts.intArray("ints", 4, 104, 101, 101, 410, 102.5, 102.5),
   220  				asserts.dateArray("dates", 4),
   221  			},
   222  		}
   223  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
   224  		expectedNoResultsAssertions := map[string][]assertFunc{}
   225  
   226  		testCases := []aggregateTestCase{
   227  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   228  
   229  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   230  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
   231  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   232  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
   233  
   234  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
   235  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
   236  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   237  
   238  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
   239  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
   240  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   241  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
   242  		}
   243  
   244  		for _, tc := range testCases {
   245  			query := aggregateArrayClassQuery(tc.filters, "groupBy: [\"ints\"]")
   246  
   247  			t.Run(tc.name, func(t *testing.T) {
   248  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   249  				extracted := extractArrayClassGroupByResult(result)
   250  
   251  				assert.Len(t, extracted, len(tc.groupedAssertions))
   252  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   253  					group := findGroup(groupedBy, extracted)
   254  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   255  
   256  					for _, assertion := range groupAssertions {
   257  						assertion(group)
   258  					}
   259  				}
   260  			})
   261  		}
   262  	})
   263  
   264  	t.Run("aggregate ArrayClass with group by numbers", func(t *testing.T) {
   265  		expectedAllResultsAssertions := map[string][]assertFunc{
   266  			"1": {
   267  				asserts.groupedBy("1", "numbers"),
   268  				asserts.meta(4),
   269  				asserts.booleanArray("booleans", 10, 4, 6, 0.4, 0.6),
   270  				asserts.textArray("texts", 10, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{4, 3, 2, 1}),
   271  				asserts.numberArray("numbers", 10, 4, 1, 1, 20, 2, 2),
   272  				asserts.intArray("ints", 10, 104, 101, 101, 1020, 102, 102),
   273  				asserts.dateArray("dates", 10),
   274  			},
   275  			"2": {
   276  				asserts.groupedBy("2", "numbers"),
   277  				asserts.meta(3),
   278  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   279  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{3, 3, 2, 1}),
   280  				asserts.numberArray("numbers", 9, 4, 1, 1, 19, 2, 2.111111111111111),
   281  				asserts.intArray("ints", 9, 104, 101, 101, 919, 102, 102.11111111111111),
   282  				asserts.dateArray("dates", 9),
   283  			},
   284  			"3": {
   285  				asserts.groupedBy("3", "numbers"),
   286  				asserts.meta(2),
   287  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   288  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   289  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   290  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   291  				asserts.dateArray("dates", 7),
   292  			},
   293  			"4": {
   294  				asserts.groupedBy("4", "numbers"),
   295  				asserts.meta(1),
   296  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   297  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{1, 1, 1, 1}),
   298  				asserts.numberArray("numbers", 4, 4, 1, 1, 10, 2.5, 2.5),
   299  				asserts.intArray("ints", 4, 104, 101, 101, 410, 102.5, 102.5),
   300  				asserts.dateArray("dates", 4),
   301  			},
   302  		}
   303  		expectedResultsWithDataAssertions := map[string][]assertFunc{
   304  			"1": {
   305  				asserts.groupedBy("1", "numbers"),
   306  				asserts.meta(2),
   307  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   308  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   309  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   310  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   311  				asserts.dateArray("dates", 7),
   312  			},
   313  			"2": {
   314  				asserts.groupedBy("2", "numbers"),
   315  				asserts.meta(2),
   316  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   317  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   318  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   319  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   320  				asserts.dateArray("dates", 7),
   321  			},
   322  			"3": {
   323  				asserts.groupedBy("3", "numbers"),
   324  				asserts.meta(2),
   325  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   326  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   327  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   328  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   329  				asserts.dateArray("dates", 7),
   330  			},
   331  			"4": {
   332  				asserts.groupedBy("4", "numbers"),
   333  				asserts.meta(1),
   334  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   335  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{1, 1, 1, 1}),
   336  				asserts.numberArray("numbers", 4, 4, 1, 1, 10, 2.5, 2.5),
   337  				asserts.intArray("ints", 4, 104, 101, 101, 410, 102.5, 102.5),
   338  				asserts.dateArray("dates", 4),
   339  			},
   340  		}
   341  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
   342  		expectedNoResultsAssertions := map[string][]assertFunc{}
   343  
   344  		testCases := []aggregateTestCase{
   345  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   346  
   347  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   348  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
   349  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   350  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
   351  
   352  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
   353  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
   354  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   355  
   356  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
   357  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
   358  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   359  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
   360  		}
   361  
   362  		for _, tc := range testCases {
   363  			query := aggregateArrayClassQuery(tc.filters, "groupBy: [\"numbers\"]")
   364  
   365  			t.Run(tc.name, func(t *testing.T) {
   366  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   367  				extracted := extractArrayClassGroupByResult(result)
   368  
   369  				assert.Len(t, extracted, len(tc.groupedAssertions))
   370  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   371  					group := findGroup(groupedBy, extracted)
   372  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   373  
   374  					for _, assertion := range groupAssertions {
   375  						assertion(group)
   376  					}
   377  				}
   378  			})
   379  		}
   380  	})
   381  
   382  	t.Run("aggregate ArrayClass with group by dates", func(t *testing.T) {
   383  		expectedAllResultsAssertions := map[string][]assertFunc{
   384  			"2021-06-01T22:18:59.640162Z": {
   385  				asserts.groupedBy("2021-06-01T22:18:59.640162Z", "dates"),
   386  				asserts.meta(4),
   387  				asserts.booleanArray("booleans", 10, 4, 6, 0.4, 0.6),
   388  				asserts.textArray("texts", 10, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{4, 3, 2, 1}),
   389  				asserts.numberArray("numbers", 10, 4, 1, 1, 20, 2, 2),
   390  				asserts.intArray("ints", 10, 104, 101, 101, 1020, 102, 102),
   391  				asserts.dateArray("dates", 10),
   392  			},
   393  			"2022-06-02T22:18:59.640162Z": {
   394  				asserts.groupedBy("2022-06-02T22:18:59.640162Z", "dates"),
   395  				asserts.meta(3),
   396  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   397  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{3, 3, 2, 1}),
   398  				asserts.numberArray("numbers", 9, 4, 1, 1, 19, 2, 2.111111111111111),
   399  				asserts.intArray("ints", 9, 104, 101, 101, 919, 102, 102.11111111111111),
   400  				asserts.dateArray("dates", 9),
   401  			},
   402  			"2023-06-03T22:18:59.640162Z": {
   403  				asserts.groupedBy("2023-06-03T22:18:59.640162Z", "dates"),
   404  				asserts.meta(2),
   405  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   406  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   407  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   408  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   409  				asserts.dateArray("dates", 7),
   410  			},
   411  			"2024-06-04T22:18:59.640162Z": {
   412  				asserts.groupedBy("2024-06-04T22:18:59.640162Z", "dates"),
   413  				asserts.meta(1),
   414  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   415  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{1, 1, 1, 1}),
   416  				asserts.numberArray("numbers", 4, 4, 1, 1, 10, 2.5, 2.5),
   417  				asserts.intArray("ints", 4, 104, 101, 101, 410, 102.5, 102.5),
   418  				asserts.dateArray("dates", 4),
   419  			},
   420  		}
   421  		expectedResultsWithDataAssertions := map[string][]assertFunc{
   422  			"2021-06-01T22:18:59.640162Z": {
   423  				asserts.groupedBy("2021-06-01T22:18:59.640162Z", "dates"),
   424  				asserts.meta(2),
   425  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   426  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   427  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   428  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   429  				asserts.dateArray("dates", 7),
   430  			},
   431  			"2022-06-02T22:18:59.640162Z": {
   432  				asserts.groupedBy("2022-06-02T22:18:59.640162Z", "dates"),
   433  				asserts.meta(2),
   434  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   435  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   436  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   437  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   438  				asserts.dateArray("dates", 7),
   439  			},
   440  			"2023-06-03T22:18:59.640162Z": {
   441  				asserts.groupedBy("2023-06-03T22:18:59.640162Z", "dates"),
   442  				asserts.meta(2),
   443  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   444  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   445  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   446  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   447  				asserts.dateArray("dates", 7),
   448  			},
   449  			"2024-06-04T22:18:59.640162Z": {
   450  				asserts.groupedBy("2024-06-04T22:18:59.640162Z", "dates"),
   451  				asserts.meta(1),
   452  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   453  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{1, 1, 1, 1}),
   454  				asserts.numberArray("numbers", 4, 4, 1, 1, 10, 2.5, 2.5),
   455  				asserts.intArray("ints", 4, 104, 101, 101, 410, 102.5, 102.5),
   456  				asserts.dateArray("dates", 4),
   457  			},
   458  		}
   459  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
   460  		expectedNoResultsAssertions := map[string][]assertFunc{}
   461  
   462  		testCases := []aggregateTestCase{
   463  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   464  
   465  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   466  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
   467  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   468  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
   469  
   470  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
   471  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
   472  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   473  
   474  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
   475  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
   476  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   477  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
   478  		}
   479  
   480  		for _, tc := range testCases {
   481  			query := aggregateArrayClassQuery(tc.filters, "groupBy: [\"dates\"]")
   482  
   483  			t.Run(tc.name, func(t *testing.T) {
   484  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   485  				extracted := extractArrayClassGroupByResult(result)
   486  
   487  				assert.Len(t, extracted, len(tc.groupedAssertions))
   488  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   489  					group := findGroup(groupedBy, extracted)
   490  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   491  
   492  					for _, assertion := range groupAssertions {
   493  						assertion(group)
   494  					}
   495  				}
   496  			})
   497  		}
   498  	})
   499  
   500  	t.Run("aggregate ArrayClass with group by booleans", func(t *testing.T) {
   501  		expectedAllResultsAssertions := map[string][]assertFunc{
   502  			"true": {
   503  				asserts.groupedBy("true", "booleans"),
   504  				asserts.meta(3),
   505  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   506  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{3, 3, 2, 1}),
   507  				asserts.numberArray("numbers", 9, 4, 1, 1, 19, 2, 2.111111111111111),
   508  				asserts.intArray("ints", 9, 104, 101, 101, 919, 102, 102.11111111111111),
   509  				asserts.dateArray("dates", 9),
   510  			},
   511  			"false": {
   512  				asserts.groupedBy("false", "booleans"),
   513  				asserts.meta(4),
   514  				asserts.booleanArray("booleans", 10, 4, 6, 0.4, 0.6),
   515  				asserts.textArray("texts", 10, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{4, 3, 2, 1}),
   516  				asserts.numberArray("numbers", 10, 4, 1, 1, 20, 2, 2),
   517  				asserts.intArray("ints", 10, 104, 101, 101, 1020, 102, 102),
   518  				asserts.dateArray("dates", 10),
   519  			},
   520  		}
   521  		expectedResultsWithDataAssertions := map[string][]assertFunc{
   522  			"true": {
   523  				asserts.groupedBy("true", "booleans"),
   524  				asserts.meta(2),
   525  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   526  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   527  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   528  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   529  				asserts.dateArray("dates", 7),
   530  			},
   531  			"false": {
   532  				asserts.groupedBy("false", "booleans"),
   533  				asserts.meta(2),
   534  				asserts.booleanArray("booleans", 7, 2, 5, 0.2857142857142857, 0.7142857142857143),
   535  				asserts.textArray("texts", 7, []string{"Alpha", "Bravo", "Charlie", "Delta"}, []int64{2, 2, 2, 1}),
   536  				asserts.numberArray("numbers", 7, 4, 1, 1, 16, 2, 2.2857142857142856),
   537  				asserts.intArray("ints", 7, 104, 101, 101, 716, 102, 102.28571428571429),
   538  				asserts.dateArray("dates", 7),
   539  			},
   540  		}
   541  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
   542  		expectedNoResultsAssertions := map[string][]assertFunc{}
   543  
   544  		testCases := []aggregateTestCase{
   545  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   546  
   547  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   548  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
   549  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   550  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
   551  
   552  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
   553  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
   554  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   555  
   556  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
   557  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
   558  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
   559  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
   560  		}
   561  
   562  		for _, tc := range testCases {
   563  			query := aggregateArrayClassQuery(tc.filters, "groupBy: [\"booleans\"]")
   564  
   565  			t.Run(tc.name, func(t *testing.T) {
   566  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   567  				extracted := extractArrayClassGroupByResult(result)
   568  
   569  				assert.Len(t, extracted, len(tc.groupedAssertions))
   570  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   571  					group := findGroup(groupedBy, extracted)
   572  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   573  
   574  					for _, assertion := range groupAssertions {
   575  						assertion(group)
   576  					}
   577  				}
   578  			})
   579  		}
   580  	})
   581  }
   582  
   583  func aggregateDuplicatesClassWithGroupByTest(t *testing.T) {
   584  	asserts := newAggregateResponseAssert(t)
   585  	testCasesGen := &aggregateDuplicatesClassTestCases{}
   586  
   587  	t.Run("aggregate DuplicatesClass with group by texts", func(t *testing.T) {
   588  		expectedAllResultsAssertions := map[string][]assertFunc{
   589  			"Alpha": {
   590  				asserts.groupedBy("Alpha", "texts"),
   591  				asserts.meta(3),
   592  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   593  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   594  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   595  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   596  				asserts.dateArray("dates", 9),
   597  			},
   598  			"Bravo": {
   599  				asserts.groupedBy("Bravo", "texts"),
   600  				asserts.meta(3),
   601  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   602  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   603  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   604  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   605  				asserts.dateArray("dates", 9),
   606  			},
   607  		}
   608  		expectedSomeResultsAssertions := map[string][]assertFunc{
   609  			"Alpha": {
   610  				asserts.groupedBy("Alpha", "texts"),
   611  				asserts.meta(1),
   612  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   613  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   614  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   615  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   616  				asserts.dateArray("dates", 4),
   617  			},
   618  			"Bravo": {
   619  				asserts.groupedBy("Bravo", "texts"),
   620  				asserts.meta(1),
   621  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   622  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   623  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   624  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   625  				asserts.dateArray("dates", 4),
   626  			},
   627  		}
   628  		expectedNoResultsAssertsions := map[string][]assertFunc{}
   629  
   630  		testCases := []aggregateTestCase{
   631  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   632  
   633  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   634  			testCasesGen.WithWhereFilter_SomeResults(expectedSomeResultsAssertions),
   635  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertsions),
   636  		}
   637  
   638  		for _, tc := range testCases {
   639  			query := aggregateDuplicatesClassQuery(tc.filters, "groupBy: [\"texts\"]")
   640  
   641  			t.Run(tc.name, func(t *testing.T) {
   642  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   643  				extracted := extractDuplicatesClassGroupByResult(result)
   644  
   645  				assert.Len(t, extracted, len(tc.groupedAssertions))
   646  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   647  					group := findGroup(groupedBy, extracted)
   648  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   649  
   650  					for _, assertion := range groupAssertions {
   651  						assertion(group)
   652  					}
   653  				}
   654  			})
   655  		}
   656  	})
   657  
   658  	t.Run("aggregate DuplicatesClass with group by ints", func(t *testing.T) {
   659  		expectedAllResultsAssertions := map[string][]assertFunc{
   660  			"101": {
   661  				asserts.groupedBy("101", "ints"),
   662  				asserts.meta(3),
   663  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   664  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   665  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   666  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   667  				asserts.dateArray("dates", 9),
   668  			},
   669  			"102": {
   670  				asserts.groupedBy("102", "ints"),
   671  				asserts.meta(3),
   672  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   673  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   674  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   675  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   676  				asserts.dateArray("dates", 9),
   677  			},
   678  		}
   679  		expectedSomeResultsAssertions := map[string][]assertFunc{
   680  			"101": {
   681  				asserts.groupedBy("101", "ints"),
   682  				asserts.meta(1),
   683  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   684  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   685  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   686  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   687  				asserts.dateArray("dates", 4),
   688  			},
   689  			"102": {
   690  				asserts.groupedBy("102", "ints"),
   691  				asserts.meta(1),
   692  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   693  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   694  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   695  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   696  				asserts.dateArray("dates", 4),
   697  			},
   698  		}
   699  		expectedNoResultsAssertsions := map[string][]assertFunc{}
   700  
   701  		testCases := []aggregateTestCase{
   702  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   703  
   704  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   705  			testCasesGen.WithWhereFilter_SomeResults(expectedSomeResultsAssertions),
   706  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertsions),
   707  		}
   708  
   709  		for _, tc := range testCases {
   710  			query := aggregateDuplicatesClassQuery(tc.filters, "groupBy: [\"ints\"]")
   711  
   712  			t.Run(tc.name, func(t *testing.T) {
   713  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   714  				extracted := extractDuplicatesClassGroupByResult(result)
   715  
   716  				assert.Len(t, extracted, len(tc.groupedAssertions))
   717  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   718  					group := findGroup(groupedBy, extracted)
   719  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   720  
   721  					for _, assertion := range groupAssertions {
   722  						assertion(group)
   723  					}
   724  				}
   725  			})
   726  		}
   727  	})
   728  
   729  	t.Run("aggregate DuplicatesClass with group by numbers", func(t *testing.T) {
   730  		expectedAllResultsAssertions := map[string][]assertFunc{
   731  			"1": {
   732  				asserts.groupedBy("1", "numbers"),
   733  				asserts.meta(3),
   734  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   735  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   736  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   737  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   738  				asserts.dateArray("dates", 9),
   739  			},
   740  			"2": {
   741  				asserts.groupedBy("2", "numbers"),
   742  				asserts.meta(3),
   743  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   744  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   745  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   746  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   747  				asserts.dateArray("dates", 9),
   748  			},
   749  		}
   750  		expectedSomeResultsAssertions := map[string][]assertFunc{
   751  			"1": {
   752  				asserts.groupedBy("1", "numbers"),
   753  				asserts.meta(1),
   754  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   755  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   756  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   757  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   758  				asserts.dateArray("dates", 4),
   759  			},
   760  			"2": {
   761  				asserts.groupedBy("2", "numbers"),
   762  				asserts.meta(1),
   763  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   764  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   765  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   766  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   767  				asserts.dateArray("dates", 4),
   768  			},
   769  		}
   770  		expectedNoResultsAssertsions := map[string][]assertFunc{}
   771  
   772  		testCases := []aggregateTestCase{
   773  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   774  
   775  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   776  			testCasesGen.WithWhereFilter_SomeResults(expectedSomeResultsAssertions),
   777  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertsions),
   778  		}
   779  
   780  		for _, tc := range testCases {
   781  			query := aggregateDuplicatesClassQuery(tc.filters, "groupBy: [\"numbers\"]")
   782  
   783  			t.Run(tc.name, func(t *testing.T) {
   784  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   785  				extracted := extractDuplicatesClassGroupByResult(result)
   786  
   787  				assert.Len(t, extracted, len(tc.groupedAssertions))
   788  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   789  					group := findGroup(groupedBy, extracted)
   790  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   791  
   792  					for _, assertion := range groupAssertions {
   793  						assertion(group)
   794  					}
   795  				}
   796  			})
   797  		}
   798  	})
   799  
   800  	t.Run("aggregate DuplicatesClass with group by dates as string", func(t *testing.T) {
   801  		expectedAllResultsAssertions := map[string][]assertFunc{
   802  			"2021-06-01T22:18:59.640162Z": {
   803  				asserts.groupedBy("2021-06-01T22:18:59.640162Z", "dates"),
   804  				asserts.meta(3),
   805  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   806  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   807  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   808  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   809  				asserts.dateArray("dates", 9),
   810  			},
   811  			"2022-06-02T22:18:59.640162Z": {
   812  				asserts.groupedBy("2022-06-02T22:18:59.640162Z", "dates"),
   813  				asserts.meta(3),
   814  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   815  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   816  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   817  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   818  				asserts.dateArray("dates", 9),
   819  			},
   820  		}
   821  		expectedSomeResultsAssertions := map[string][]assertFunc{
   822  			"2021-06-01T22:18:59.640162Z": {
   823  				asserts.groupedBy("2021-06-01T22:18:59.640162Z", "dates"),
   824  				asserts.meta(1),
   825  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   826  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   827  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   828  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   829  				asserts.dateArray("dates", 4),
   830  			},
   831  			"2022-06-02T22:18:59.640162Z": {
   832  				asserts.groupedBy("2022-06-02T22:18:59.640162Z", "dates"),
   833  				asserts.meta(1),
   834  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   835  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   836  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   837  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   838  				asserts.dateArray("dates", 4),
   839  			},
   840  		}
   841  		expectedNoResultsAssertsions := map[string][]assertFunc{}
   842  
   843  		testCases := []aggregateTestCase{
   844  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   845  
   846  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   847  			testCasesGen.WithWhereFilter_SomeResults(expectedSomeResultsAssertions),
   848  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertsions),
   849  		}
   850  
   851  		for _, tc := range testCases {
   852  			query := aggregateDuplicatesClassQuery(tc.filters, "groupBy: [\"dates\"]")
   853  
   854  			t.Run(tc.name, func(t *testing.T) {
   855  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   856  				extracted := extractDuplicatesClassGroupByResult(result)
   857  
   858  				assert.Len(t, extracted, len(tc.groupedAssertions))
   859  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   860  					group := findGroup(groupedBy, extracted)
   861  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   862  
   863  					for _, assertion := range groupAssertions {
   864  						assertion(group)
   865  					}
   866  				}
   867  			})
   868  		}
   869  	})
   870  
   871  	t.Run("aggregate DuplicatesClass with group by booleans", func(t *testing.T) {
   872  		expectedAllResultsAssertions := map[string][]assertFunc{
   873  			"true": {
   874  				asserts.groupedBy("true", "booleans"),
   875  				asserts.meta(3),
   876  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   877  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   878  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   879  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   880  				asserts.dateArray("dates", 9),
   881  			},
   882  			"false": {
   883  				asserts.groupedBy("false", "booleans"),
   884  				asserts.meta(3),
   885  				asserts.booleanArray("booleans", 9, 3, 6, 0.3333333333333333, 0.6666666666666666),
   886  				asserts.textArray("texts", 9, []string{"Alpha", "Bravo"}, []int64{6, 3}),
   887  				asserts.numberArray("numbers", 9, 2, 1, 1, 12, 1, 1.3333333333333333),
   888  				asserts.intArray("ints", 9, 102, 101, 101, 912, 101, 101.33333333333333),
   889  				asserts.dateArray("dates", 9),
   890  			},
   891  		}
   892  		expectedSomeResultsAssertions := map[string][]assertFunc{
   893  			"true": {
   894  				asserts.groupedBy("true", "booleans"),
   895  				asserts.meta(1),
   896  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   897  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   898  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   899  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   900  				asserts.dateArray("dates", 4),
   901  			},
   902  			"false": {
   903  				asserts.groupedBy("false", "booleans"),
   904  				asserts.meta(1),
   905  				asserts.booleanArray("booleans", 4, 1, 3, 0.25, 0.75),
   906  				asserts.textArray("texts", 4, []string{"Alpha", "Bravo"}, []int64{3, 1}),
   907  				asserts.numberArray("numbers", 4, 2, 1, 1, 5, 1, 1.25),
   908  				asserts.intArray("ints", 4, 102, 101, 101, 405, 101, 101.25),
   909  				asserts.dateArray("dates", 4),
   910  			},
   911  		}
   912  		expectedNoResultsAssertsions := map[string][]assertFunc{}
   913  
   914  		testCases := []aggregateTestCase{
   915  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
   916  
   917  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
   918  			testCasesGen.WithWhereFilter_SomeResults(expectedSomeResultsAssertions),
   919  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertsions),
   920  		}
   921  
   922  		for _, tc := range testCases {
   923  			query := aggregateDuplicatesClassQuery(tc.filters, "groupBy: [\"booleans\"]")
   924  
   925  			t.Run(tc.name, func(t *testing.T) {
   926  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
   927  				extracted := extractDuplicatesClassGroupByResult(result)
   928  
   929  				assert.Len(t, extracted, len(tc.groupedAssertions))
   930  				for groupedBy, groupAssertions := range tc.groupedAssertions {
   931  					group := findGroup(groupedBy, extracted)
   932  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
   933  
   934  					for _, assertion := range groupAssertions {
   935  						assertion(group)
   936  					}
   937  				}
   938  			})
   939  		}
   940  	})
   941  }
   942  
   943  func aggregateCityClassWithGroupByTest(t *testing.T) {
   944  	t.Run("aggregate City with group by city area", func(t *testing.T) {
   945  		asserts := newAggregateResponseAssert(t)
   946  		testCasesGen := &aggregateCityTestCases{}
   947  
   948  		expectedAllResultsAssertions := map[string][]assertFunc{
   949  			"891.96": {
   950  				asserts.groupedBy("891.96", "cityArea"),
   951  				asserts.meta(1),
   952  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
   953  				asserts.date("cityRights", 1),
   954  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
   955  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
   956  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
   957  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
   958  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
   959  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
   960  				asserts.pointingTo("inCountry", "Country"),
   961  			},
   962  			"891.95": {
   963  				asserts.groupedBy("891.95", "cityArea"),
   964  				asserts.meta(1),
   965  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
   966  				asserts.date("cityRights", 1),
   967  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
   968  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
   969  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
   970  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
   971  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
   972  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
   973  				asserts.pointingTo("inCountry", "Country"),
   974  			},
   975  			"217.22": {
   976  				asserts.groupedBy("217.22", "cityArea"),
   977  				asserts.meta(1),
   978  				asserts.number("cityArea", 1, 217.22, 217.22, 217.22, 217.22, 217.22, 217.22),
   979  				asserts.date("cityRights", 1),
   980  				asserts.text("history", 1, []string{historyDusseldorf}, []int64{1}),
   981  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
   982  				asserts.textArray("museums", 3, []string{"Onomato", "Schiffahrt Museum", "Schlossturm"}, []int64{1, 1, 1}),
   983  				asserts.text("name", 1, []string{"Dusseldorf"}, []int64{1}),
   984  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
   985  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
   986  				asserts.pointingTo("inCountry", "Country"),
   987  			},
   988  			"319.35": {
   989  				asserts.groupedBy("319.35", "cityArea"),
   990  				asserts.meta(1),
   991  				asserts.number("cityArea", 1, 319.35, 319.35, 319.35, 319.35, 319.35, 319.35),
   992  				asserts.date("cityRights", 1),
   993  				asserts.text("history", 1, []string{historyRotterdam}, []int64{1}),
   994  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
   995  				asserts.textArray("museums", 3, []string{"Museum Boijmans Van Beuningen", "Wereldmuseum", "Witte de With Center for Contemporary Art"}, []int64{1, 1, 1}),
   996  				asserts.text("name", 1, []string{"Rotterdam"}, []int64{1}),
   997  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
   998  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
   999  				asserts.pointingTo("inCountry", "Country"),
  1000  			},
  1001  		}
  1002  		expectedResultsWithDataAssertions := map[string][]assertFunc{
  1003  			"891.96": {
  1004  				asserts.groupedBy("891.96", "cityArea"),
  1005  				asserts.meta(1),
  1006  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1007  				asserts.date("cityRights", 1),
  1008  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1009  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1010  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1011  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1012  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1013  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1014  				asserts.pointingTo("inCountry", "Country"),
  1015  			},
  1016  			"891.95": {
  1017  				asserts.groupedBy("891.95", "cityArea"),
  1018  				asserts.meta(1),
  1019  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1020  				asserts.date("cityRights", 1),
  1021  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1022  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1023  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1024  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1025  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1026  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1027  				asserts.pointingTo("inCountry", "Country"),
  1028  			},
  1029  		}
  1030  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
  1031  		expectedNoResultsAssertions := map[string][]assertFunc{}
  1032  
  1033  		testCases := []aggregateTestCase{
  1034  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
  1035  
  1036  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
  1037  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1038  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1039  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
  1040  
  1041  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
  1042  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1043  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1044  
  1045  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
  1046  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
  1047  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1048  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
  1049  		}
  1050  
  1051  		for _, tc := range testCases {
  1052  			query := aggregateCityQuery(tc.filters, "groupBy: [\"cityArea\"]")
  1053  
  1054  			t.Run(tc.name, func(t *testing.T) {
  1055  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
  1056  				extracted := extractCityGroupByResult(result)
  1057  
  1058  				assert.Len(t, extracted, len(tc.groupedAssertions))
  1059  				for groupedBy, groupAssertions := range tc.groupedAssertions {
  1060  					group := findGroup(groupedBy, extracted)
  1061  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
  1062  
  1063  					for _, assertion := range groupAssertions {
  1064  						assertion(group)
  1065  					}
  1066  				}
  1067  			})
  1068  		}
  1069  	})
  1070  
  1071  	t.Run("aggregate City with group by history", func(t *testing.T) {
  1072  		asserts := newAggregateResponseAssert(t)
  1073  		testCasesGen := &aggregateCityTestCases{}
  1074  
  1075  		expectedAllResultsAssertions := map[string][]assertFunc{
  1076  			historyBerlin: {
  1077  				asserts.groupedBy(historyBerlin, "history"),
  1078  				asserts.meta(1),
  1079  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1080  				asserts.date("cityRights", 1),
  1081  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1082  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1083  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1084  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1085  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1086  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1087  				asserts.pointingTo("inCountry", "Country"),
  1088  			},
  1089  			historyAmsterdam: {
  1090  				asserts.groupedBy(historyAmsterdam, "history"),
  1091  				asserts.meta(1),
  1092  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1093  				asserts.date("cityRights", 1),
  1094  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1095  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1096  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1097  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1098  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1099  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1100  				asserts.pointingTo("inCountry", "Country"),
  1101  			},
  1102  			historyDusseldorf: {
  1103  				asserts.groupedBy(historyDusseldorf, "history"),
  1104  				asserts.meta(1),
  1105  				asserts.number("cityArea", 1, 217.22, 217.22, 217.22, 217.22, 217.22, 217.22),
  1106  				asserts.date("cityRights", 1),
  1107  				asserts.text("history", 1, []string{historyDusseldorf}, []int64{1}),
  1108  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1109  				asserts.textArray("museums", 3, []string{"Onomato", "Schiffahrt Museum", "Schlossturm"}, []int64{1, 1, 1}),
  1110  				asserts.text("name", 1, []string{"Dusseldorf"}, []int64{1}),
  1111  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1112  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1113  				asserts.pointingTo("inCountry", "Country"),
  1114  			},
  1115  			historyRotterdam: {
  1116  				asserts.groupedBy(historyRotterdam, "history"),
  1117  				asserts.meta(1),
  1118  				asserts.number("cityArea", 1, 319.35, 319.35, 319.35, 319.35, 319.35, 319.35),
  1119  				asserts.date("cityRights", 1),
  1120  				asserts.text("history", 1, []string{historyRotterdam}, []int64{1}),
  1121  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1122  				asserts.textArray("museums", 3, []string{"Museum Boijmans Van Beuningen", "Wereldmuseum", "Witte de With Center for Contemporary Art"}, []int64{1, 1, 1}),
  1123  				asserts.text("name", 1, []string{"Rotterdam"}, []int64{1}),
  1124  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1125  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1126  				asserts.pointingTo("inCountry", "Country"),
  1127  			},
  1128  		}
  1129  		expectedResultsWithDataAssertions := map[string][]assertFunc{
  1130  			historyBerlin: {
  1131  				asserts.groupedBy(historyBerlin, "history"),
  1132  				asserts.meta(1),
  1133  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1134  				asserts.date("cityRights", 1),
  1135  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1136  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1137  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1138  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1139  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1140  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1141  				asserts.pointingTo("inCountry", "Country"),
  1142  			},
  1143  			historyAmsterdam: {
  1144  				asserts.groupedBy(historyAmsterdam, "history"),
  1145  				asserts.meta(1),
  1146  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1147  				asserts.date("cityRights", 1),
  1148  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1149  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1150  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1151  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1152  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1153  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1154  				asserts.pointingTo("inCountry", "Country"),
  1155  			},
  1156  		}
  1157  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
  1158  		expectedNoResultsAssertions := map[string][]assertFunc{}
  1159  
  1160  		testCases := []aggregateTestCase{
  1161  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
  1162  
  1163  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
  1164  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1165  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1166  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
  1167  
  1168  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
  1169  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1170  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1171  
  1172  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
  1173  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
  1174  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1175  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
  1176  		}
  1177  
  1178  		for _, tc := range testCases {
  1179  			query := aggregateCityQuery(tc.filters, "groupBy: [\"history\"]")
  1180  
  1181  			t.Run(tc.name, func(t *testing.T) {
  1182  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
  1183  				extracted := extractCityGroupByResult(result)
  1184  
  1185  				assert.Len(t, extracted, len(tc.groupedAssertions))
  1186  				for groupedBy, groupAssertions := range tc.groupedAssertions {
  1187  					group := findGroup(groupedBy, extracted)
  1188  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
  1189  
  1190  					for _, assertion := range groupAssertions {
  1191  						assertion(group)
  1192  					}
  1193  				}
  1194  			})
  1195  		}
  1196  	})
  1197  
  1198  	t.Run("aggregate City with group by name", func(t *testing.T) {
  1199  		asserts := newAggregateResponseAssert(t)
  1200  		testCasesGen := &aggregateCityTestCases{}
  1201  
  1202  		expectedAllResultsAssertions := map[string][]assertFunc{
  1203  			"Berlin": {
  1204  				asserts.groupedBy("Berlin", "name"),
  1205  				asserts.meta(1),
  1206  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1207  				asserts.date("cityRights", 1),
  1208  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1209  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1210  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1211  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1212  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1213  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1214  				asserts.pointingTo("inCountry", "Country"),
  1215  			},
  1216  			"Amsterdam": {
  1217  				asserts.groupedBy("Amsterdam", "name"),
  1218  				asserts.meta(1),
  1219  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1220  				asserts.date("cityRights", 1),
  1221  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1222  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1223  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1224  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1225  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1226  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1227  				asserts.pointingTo("inCountry", "Country"),
  1228  			},
  1229  			"Dusseldorf": {
  1230  				asserts.groupedBy("Dusseldorf", "name"),
  1231  				asserts.meta(1),
  1232  				asserts.number("cityArea", 1, 217.22, 217.22, 217.22, 217.22, 217.22, 217.22),
  1233  				asserts.date("cityRights", 1),
  1234  				asserts.text("history", 1, []string{historyDusseldorf}, []int64{1}),
  1235  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1236  				asserts.textArray("museums", 3, []string{"Onomato", "Schiffahrt Museum", "Schlossturm"}, []int64{1, 1, 1}),
  1237  				asserts.text("name", 1, []string{"Dusseldorf"}, []int64{1}),
  1238  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1239  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1240  				asserts.pointingTo("inCountry", "Country"),
  1241  			},
  1242  			"Rotterdam": {
  1243  				asserts.groupedBy("Rotterdam", "name"),
  1244  				asserts.meta(1),
  1245  				asserts.number("cityArea", 1, 319.35, 319.35, 319.35, 319.35, 319.35, 319.35),
  1246  				asserts.date("cityRights", 1),
  1247  				asserts.text("history", 1, []string{historyRotterdam}, []int64{1}),
  1248  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1249  				asserts.textArray("museums", 3, []string{"Museum Boijmans Van Beuningen", "Wereldmuseum", "Witte de With Center for Contemporary Art"}, []int64{1, 1, 1}),
  1250  				asserts.text("name", 1, []string{"Rotterdam"}, []int64{1}),
  1251  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1252  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1253  				asserts.pointingTo("inCountry", "Country"),
  1254  			},
  1255  			"Missing Island": {
  1256  				asserts.groupedBy("Missing Island", "name"),
  1257  				asserts.meta(1),
  1258  				asserts.number0("cityArea"),
  1259  				asserts.date0("cityRights"),
  1260  				asserts.text0("history"),
  1261  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1262  				asserts.textArray0("museums"),
  1263  				asserts.text("name", 1, []string{"Missing Island"}, []int64{1}),
  1264  				asserts.int("population", 1, 0, 0, 0, 0, 0, 0),
  1265  				asserts.textArray0("timezones"),
  1266  				asserts.pointingTo("inCountry", "Country"),
  1267  			},
  1268  		}
  1269  		expectedResultsWithDataAssertions := map[string][]assertFunc{
  1270  			"Berlin": {
  1271  				asserts.groupedBy("Berlin", "name"),
  1272  				asserts.meta(1),
  1273  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1274  				asserts.date("cityRights", 1),
  1275  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1276  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1277  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1278  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1279  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1280  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1281  				asserts.pointingTo("inCountry", "Country"),
  1282  			},
  1283  			"Amsterdam": {
  1284  				asserts.groupedBy("Amsterdam", "name"),
  1285  				asserts.meta(1),
  1286  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1287  				asserts.date("cityRights", 1),
  1288  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1289  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1290  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1291  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1292  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1293  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1294  				asserts.pointingTo("inCountry", "Country"),
  1295  			},
  1296  		}
  1297  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
  1298  		expectedNoResultsAssertions := map[string][]assertFunc{}
  1299  
  1300  		testCases := []aggregateTestCase{
  1301  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
  1302  
  1303  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
  1304  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1305  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1306  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
  1307  
  1308  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
  1309  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1310  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1311  
  1312  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
  1313  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
  1314  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1315  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
  1316  		}
  1317  
  1318  		for _, tc := range testCases {
  1319  			query := aggregateCityQuery(tc.filters, "groupBy: [\"name\"]")
  1320  
  1321  			t.Run(tc.name, func(t *testing.T) {
  1322  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
  1323  				extracted := extractCityGroupByResult(result)
  1324  
  1325  				assert.Len(t, extracted, len(tc.groupedAssertions))
  1326  				for groupedBy, groupAssertions := range tc.groupedAssertions {
  1327  					group := findGroup(groupedBy, extracted)
  1328  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
  1329  
  1330  					for _, assertion := range groupAssertions {
  1331  						assertion(group)
  1332  					}
  1333  				}
  1334  			})
  1335  		}
  1336  	})
  1337  
  1338  	t.Run("aggregate City with group by is capital", func(t *testing.T) {
  1339  		asserts := newAggregateResponseAssert(t)
  1340  		testCasesGen := &aggregateCityTestCases{}
  1341  
  1342  		expectedAllResultsAssertions := map[string][]assertFunc{
  1343  			"true": {
  1344  				asserts.groupedBy("true", "isCapital"),
  1345  				asserts.meta(2),
  1346  				asserts.number("cityArea", 2, 891.96, 891.95, 891.95, 1783.91, 891.955, 891.955),
  1347  				asserts.date("cityRights", 2),
  1348  				asserts.text("history", 2, []string{historyAmsterdam, historyBerlin}, []int64{1, 1}),
  1349  				asserts.boolean("isCapital", 2, 0, 2, 0, 1),
  1350  				asserts.textArray("museums", 3, []string{"German Historical Museum", "Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1, 1}),
  1351  				asserts.text("name", 2, []string{"Amsterdam", "Berlin"}, []int64{1, 1}),
  1352  				asserts.int("population", 2, 3470000, 1800000, 1800000, 5270000, 2635000, 2635000),
  1353  				asserts.textArray("timezones", 4, []string{"CEST", "CET"}, []int64{2, 2}),
  1354  				asserts.pointingTo("inCountry", "Country"),
  1355  			},
  1356  			"false": {
  1357  				asserts.groupedBy("false", "isCapital"),
  1358  				asserts.meta(3),
  1359  				asserts.number("cityArea", 2, 319.35, 217.22, 217.22, 536.57, 268.285, 268.285),
  1360  				asserts.date("cityRights", 2),
  1361  				asserts.text("history", 2, []string{historyRotterdam, historyDusseldorf}, []int64{1, 1}),
  1362  				asserts.boolean("isCapital", 3, 3, 0, 1, 0),
  1363  				asserts.textArray("museums", 6, []string{"Museum Boijmans Van Beuningen", "Onomato", "Schiffahrt Museum", "Schlossturm", "Wereldmuseum"}, []int64{1, 1, 1, 1, 1}),
  1364  				asserts.text("name", 3, []string{"Dusseldorf", "Missing Island", "Rotterdam"}, []int64{1, 1, 1}),
  1365  				asserts.int("population", 3, 600000, 0, 600000, 1200000, 600000, 400000),
  1366  				asserts.textArray("timezones", 4, []string{"CEST", "CET"}, []int64{2, 2}),
  1367  				asserts.pointingTo("inCountry", "Country"),
  1368  			},
  1369  		}
  1370  		expectedResultsWithDataAssertions := map[string][]assertFunc{
  1371  			"true": {
  1372  				asserts.groupedBy("true", "isCapital"),
  1373  				asserts.meta(2),
  1374  				asserts.number("cityArea", 2, 891.96, 891.95, 891.95, 1783.91, 891.955, 891.955),
  1375  				asserts.date("cityRights", 2),
  1376  				asserts.text("history", 2, []string{historyAmsterdam, historyBerlin}, []int64{1, 1}),
  1377  				asserts.boolean("isCapital", 2, 0, 2, 0, 1),
  1378  				asserts.textArray("museums", 3, []string{"German Historical Museum", "Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1, 1}),
  1379  				asserts.text("name", 2, []string{"Amsterdam", "Berlin"}, []int64{1, 1}),
  1380  				asserts.int("population", 2, 3470000, 1800000, 1800000, 5270000, 2635000, 2635000),
  1381  				asserts.textArray("timezones", 4, []string{"CEST", "CET"}, []int64{2, 2}),
  1382  				asserts.pointingTo("inCountry", "Country"),
  1383  			},
  1384  		}
  1385  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
  1386  		expectedNoResultsAssertions := map[string][]assertFunc{}
  1387  
  1388  		testCases := []aggregateTestCase{
  1389  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
  1390  
  1391  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
  1392  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1393  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1394  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
  1395  
  1396  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
  1397  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1398  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1399  
  1400  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
  1401  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
  1402  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1403  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
  1404  		}
  1405  
  1406  		for _, tc := range testCases {
  1407  			query := aggregateCityQuery(tc.filters, "groupBy: [\"isCapital\"]")
  1408  
  1409  			t.Run(tc.name, func(t *testing.T) {
  1410  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
  1411  				extracted := extractCityGroupByResult(result)
  1412  
  1413  				assert.Len(t, extracted, len(tc.groupedAssertions))
  1414  				for groupedBy, groupAssertions := range tc.groupedAssertions {
  1415  					group := findGroup(groupedBy, extracted)
  1416  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
  1417  
  1418  					for _, assertion := range groupAssertions {
  1419  						assertion(group)
  1420  					}
  1421  				}
  1422  			})
  1423  		}
  1424  	})
  1425  
  1426  	t.Run("aggregate City with group by name", func(t *testing.T) {
  1427  		asserts := newAggregateResponseAssert(t)
  1428  		testCasesGen := &aggregateCityTestCases{}
  1429  
  1430  		expectedAllResultsAssertions := map[string][]assertFunc{
  1431  			"1400-01-01T00:00:00+02:00": {
  1432  				asserts.groupedBy("1400-01-01T00:00:00+02:00", "cityRights"),
  1433  				asserts.meta(2),
  1434  				asserts.number("cityArea", 2, 891.96, 891.95, 891.95, 1783.91, 891.955, 891.955),
  1435  				asserts.date("cityRights", 2),
  1436  				asserts.text("history", 2, []string{historyAmsterdam, historyBerlin}, []int64{1, 1}),
  1437  				asserts.boolean("isCapital", 2, 0, 2, 0, 1),
  1438  				asserts.textArray("museums", 3, []string{"German Historical Museum", "Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1, 1}),
  1439  				asserts.text("name", 2, []string{"Amsterdam", "Berlin"}, []int64{1, 1}),
  1440  				asserts.int("population", 2, 3470000, 1800000, 1800000, 5270000, 2635000, 2635000),
  1441  				asserts.textArray("timezones", 4, []string{"CEST", "CET"}, []int64{2, 2}),
  1442  				asserts.pointingTo("inCountry", "Country"),
  1443  			},
  1444  			"1135-01-01T00:00:00+02:00": {
  1445  				asserts.groupedBy("1135-01-01T00:00:00+02:00", "cityRights"),
  1446  				asserts.meta(1),
  1447  				asserts.number("cityArea", 1, 217.22, 217.22, 217.22, 217.22, 217.22, 217.22),
  1448  				asserts.date("cityRights", 1),
  1449  				asserts.text("history", 1, []string{historyDusseldorf}, []int64{1}),
  1450  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1451  				asserts.textArray("museums", 3, []string{"Onomato", "Schiffahrt Museum", "Schlossturm"}, []int64{1, 1, 1}),
  1452  				asserts.text("name", 1, []string{"Dusseldorf"}, []int64{1}),
  1453  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1454  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1455  				asserts.pointingTo("inCountry", "Country"),
  1456  			},
  1457  			"1283-01-01T00:00:00+02:00": {
  1458  				asserts.groupedBy("1283-01-01T00:00:00+02:00", "cityRights"),
  1459  				asserts.meta(1),
  1460  				asserts.number("cityArea", 1, 319.35, 319.35, 319.35, 319.35, 319.35, 319.35),
  1461  				asserts.date("cityRights", 1),
  1462  				asserts.text("history", 1, []string{historyRotterdam}, []int64{1}),
  1463  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1464  				asserts.textArray("museums", 3, []string{"Museum Boijmans Van Beuningen", "Wereldmuseum", "Witte de With Center for Contemporary Art"}, []int64{1, 1, 1}),
  1465  				asserts.text("name", 1, []string{"Rotterdam"}, []int64{1}),
  1466  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1467  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1468  				asserts.pointingTo("inCountry", "Country"),
  1469  			},
  1470  		}
  1471  		expectedResultsWithDataAssertions := map[string][]assertFunc{
  1472  			"1400-01-01T00:00:00+02:00": {
  1473  				asserts.groupedBy("1400-01-01T00:00:00+02:00", "cityRights"),
  1474  				asserts.meta(2),
  1475  				asserts.number("cityArea", 2, 891.96, 891.95, 891.95, 1783.91, 891.955, 891.955),
  1476  				asserts.date("cityRights", 2),
  1477  				asserts.text("history", 2, []string{historyAmsterdam, historyBerlin}, []int64{1, 1}),
  1478  				asserts.boolean("isCapital", 2, 0, 2, 0, 1),
  1479  				asserts.textArray("museums", 3, []string{"German Historical Museum", "Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1, 1}),
  1480  				asserts.text("name", 2, []string{"Amsterdam", "Berlin"}, []int64{1, 1}),
  1481  				asserts.int("population", 2, 3470000, 1800000, 1800000, 5270000, 2635000, 2635000),
  1482  				asserts.textArray("timezones", 4, []string{"CEST", "CET"}, []int64{2, 2}),
  1483  				asserts.pointingTo("inCountry", "Country"),
  1484  			},
  1485  		}
  1486  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
  1487  		expectedNoResultsAssertions := map[string][]assertFunc{}
  1488  
  1489  		testCases := []aggregateTestCase{
  1490  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
  1491  
  1492  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
  1493  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1494  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1495  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
  1496  
  1497  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
  1498  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1499  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1500  
  1501  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
  1502  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
  1503  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1504  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
  1505  		}
  1506  
  1507  		for _, tc := range testCases {
  1508  			query := aggregateCityQuery(tc.filters, "groupBy: [\"cityRights\"]")
  1509  
  1510  			t.Run(tc.name, func(t *testing.T) {
  1511  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
  1512  				extracted := extractCityGroupByResult(result)
  1513  
  1514  				assert.Len(t, extracted, len(tc.groupedAssertions))
  1515  				for groupedBy, groupAssertions := range tc.groupedAssertions {
  1516  					group := findGroup(groupedBy, extracted)
  1517  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
  1518  
  1519  					for _, assertion := range groupAssertions {
  1520  						assertion(group)
  1521  					}
  1522  				}
  1523  			})
  1524  		}
  1525  	})
  1526  
  1527  	t.Run("aggregate City with group by population", func(t *testing.T) {
  1528  		asserts := newAggregateResponseAssert(t)
  1529  		testCasesGen := &aggregateCityTestCases{}
  1530  
  1531  		expectedAllResultsAssertions := map[string][]assertFunc{
  1532  			"600000": {
  1533  				asserts.groupedBy("600000", "population"),
  1534  				asserts.meta(2),
  1535  				asserts.number("cityArea", 2, 319.35, 217.22, 217.22, 536.57, 268.285, 268.285),
  1536  				asserts.date("cityRights", 2),
  1537  				asserts.text("history", 2, []string{historyRotterdam, historyDusseldorf}, []int64{1, 1}),
  1538  				asserts.boolean("isCapital", 2, 2, 0, 1, 0),
  1539  				asserts.textArray("museums", 6, []string{"Museum Boijmans Van Beuningen", "Onomato", "Schiffahrt Museum", "Schlossturm", "Wereldmuseum"}, []int64{1, 1, 1, 1, 1}),
  1540  				asserts.text("name", 2, []string{"Dusseldorf", "Rotterdam"}, []int64{1, 1}),
  1541  				asserts.int("population", 2, 600000, 600000, 600000, 1200000, 600000, 600000),
  1542  				asserts.textArray("timezones", 4, []string{"CEST", "CET"}, []int64{2, 2}),
  1543  				asserts.pointingTo("inCountry", "Country"),
  1544  			},
  1545  			"3.47e+06": {
  1546  				asserts.groupedBy("3.47e+06", "population"),
  1547  				asserts.meta(1),
  1548  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1549  				asserts.date("cityRights", 1),
  1550  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1551  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1552  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1553  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1554  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1555  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1556  				asserts.pointingTo("inCountry", "Country"),
  1557  			},
  1558  			"1.8e+06": {
  1559  				asserts.groupedBy("1.8e+06", "population"),
  1560  				asserts.meta(1),
  1561  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1562  				asserts.date("cityRights", 1),
  1563  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1564  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1565  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1566  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1567  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1568  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1569  				asserts.pointingTo("inCountry", "Country"),
  1570  			},
  1571  			"0": {
  1572  				asserts.groupedBy("0", "population"),
  1573  				asserts.meta(1),
  1574  				asserts.number0("cityArea"),
  1575  				asserts.date0("cityRights"),
  1576  				asserts.text0("history"),
  1577  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1578  				asserts.textArray0("museums"),
  1579  				asserts.text("name", 1, []string{"Missing Island"}, []int64{1}),
  1580  				asserts.int("population", 1, 0, 0, 0, 0, 0, 0),
  1581  				asserts.textArray0("timezones"),
  1582  				asserts.pointingTo("inCountry", "Country"),
  1583  			},
  1584  		}
  1585  		expectedResultsWithDataAssertions := map[string][]assertFunc{
  1586  			"3.47e+06": {
  1587  				asserts.groupedBy("3.47e+06", "population"),
  1588  				asserts.meta(1),
  1589  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1590  				asserts.date("cityRights", 1),
  1591  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1592  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1593  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1594  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1595  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1596  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1597  				asserts.pointingTo("inCountry", "Country"),
  1598  			},
  1599  			"1.8e+06": {
  1600  				asserts.groupedBy("1.8e+06", "population"),
  1601  				asserts.meta(1),
  1602  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1603  				asserts.date("cityRights", 1),
  1604  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1605  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1606  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1607  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1608  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1609  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1610  				asserts.pointingTo("inCountry", "Country"),
  1611  			},
  1612  		}
  1613  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
  1614  		expectedNoResultsAssertions := map[string][]assertFunc{}
  1615  
  1616  		testCases := []aggregateTestCase{
  1617  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
  1618  
  1619  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
  1620  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1621  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1622  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
  1623  
  1624  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
  1625  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1626  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1627  
  1628  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
  1629  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
  1630  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1631  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
  1632  		}
  1633  
  1634  		for _, tc := range testCases {
  1635  			query := aggregateCityQuery(tc.filters, "groupBy: [\"population\"]")
  1636  
  1637  			t.Run(tc.name, func(t *testing.T) {
  1638  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
  1639  				extracted := extractCityGroupByResult(result)
  1640  
  1641  				assert.Len(t, extracted, len(tc.groupedAssertions))
  1642  				for groupedBy, groupAssertions := range tc.groupedAssertions {
  1643  					group := findGroup(groupedBy, extracted)
  1644  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
  1645  
  1646  					for _, assertion := range groupAssertions {
  1647  						assertion(group)
  1648  					}
  1649  				}
  1650  			})
  1651  		}
  1652  	})
  1653  
  1654  	t.Run("aggregate City with group by timezones", func(t *testing.T) {
  1655  		asserts := newAggregateResponseAssert(t)
  1656  		testCasesGen := &aggregateCityTestCases{}
  1657  
  1658  		expectedAllResultsAssertions := map[string][]assertFunc{
  1659  			"CEST": {
  1660  				asserts.groupedBy("CEST", "timezones"),
  1661  				asserts.meta(4),
  1662  				asserts.number("cityArea", 4, 891.96, 217.22, 217.22, 2320.48, 605.6500000000001, 580.12),
  1663  				asserts.date("cityRights", 4),
  1664  				asserts.text("history", 4, []string{historyAmsterdam, historyRotterdam, historyBerlin, historyDusseldorf}, []int64{1, 1, 1, 1}),
  1665  				asserts.boolean("isCapital", 4, 2, 2, 0.5, 0.5),
  1666  				asserts.textArray("museums", 9, []string{"German Historical Museum", "Museum Boijmans Van Beuningen", "Onomato", "Rijksmuseum", "Schiffahrt Museum"}, []int64{1, 1, 1, 1, 1}),
  1667  				asserts.text("name", 4, []string{"Amsterdam", "Berlin", "Dusseldorf", "Rotterdam"}, []int64{1, 1, 1, 1}),
  1668  				asserts.int("population", 4, 3470000, 600000, 600000, 6470000, 1200000, 1617500),
  1669  				asserts.textArray("timezones", 8, []string{"CEST", "CET"}, []int64{4, 4}),
  1670  				asserts.pointingTo("inCountry", "Country"),
  1671  			},
  1672  			"CET": {
  1673  				asserts.groupedBy("CET", "timezones"),
  1674  				asserts.meta(4),
  1675  				asserts.number("cityArea", 4, 891.96, 217.22, 217.22, 2320.48, 605.6500000000001, 580.12),
  1676  				asserts.date("cityRights", 4),
  1677  				asserts.text("history", 4, []string{historyAmsterdam, historyRotterdam, historyBerlin, historyDusseldorf}, []int64{1, 1, 1, 1}),
  1678  				asserts.boolean("isCapital", 4, 2, 2, 0.5, 0.5),
  1679  				asserts.textArray("museums", 9, []string{"German Historical Museum", "Museum Boijmans Van Beuningen", "Onomato", "Rijksmuseum", "Schiffahrt Museum"}, []int64{1, 1, 1, 1, 1}),
  1680  				asserts.text("name", 4, []string{"Amsterdam", "Berlin", "Dusseldorf", "Rotterdam"}, []int64{1, 1, 1, 1}),
  1681  				asserts.int("population", 4, 3470000, 600000, 600000, 6470000, 1200000, 1617500),
  1682  				asserts.textArray("timezones", 8, []string{"CEST", "CET"}, []int64{4, 4}),
  1683  				asserts.pointingTo("inCountry", "Country"),
  1684  			},
  1685  		}
  1686  		expectedResultsWithDataAssertions := map[string][]assertFunc{
  1687  			"CEST": {
  1688  				asserts.groupedBy("CEST", "timezones"),
  1689  				asserts.meta(2),
  1690  				asserts.number("cityArea", 2, 891.96, 891.95, 891.95, 1783.91, 891.955, 891.955),
  1691  				asserts.date("cityRights", 2),
  1692  				asserts.text("history", 2, []string{historyAmsterdam, historyBerlin}, []int64{1, 1}),
  1693  				asserts.boolean("isCapital", 2, 0, 2, 0, 1),
  1694  				asserts.textArray("museums", 3, []string{"German Historical Museum", "Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1, 1}),
  1695  				asserts.text("name", 2, []string{"Amsterdam", "Berlin"}, []int64{1, 1}),
  1696  				asserts.int("population", 2, 3470000, 1800000, 1800000, 5270000, 2635000, 2635000),
  1697  				asserts.textArray("timezones", 4, []string{"CEST", "CET"}, []int64{2, 2}),
  1698  				asserts.pointingTo("inCountry", "Country"),
  1699  			},
  1700  			"CET": {
  1701  				asserts.groupedBy("CET", "timezones"),
  1702  				asserts.meta(2),
  1703  				asserts.number("cityArea", 2, 891.96, 891.95, 891.95, 1783.91, 891.955, 891.955),
  1704  				asserts.date("cityRights", 2),
  1705  				asserts.text("history", 2, []string{historyAmsterdam, historyBerlin}, []int64{1, 1}),
  1706  				asserts.boolean("isCapital", 2, 0, 2, 0, 1),
  1707  				asserts.textArray("museums", 3, []string{"German Historical Museum", "Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1, 1}),
  1708  				asserts.text("name", 2, []string{"Amsterdam", "Berlin"}, []int64{1, 1}),
  1709  				asserts.int("population", 2, 3470000, 1800000, 1800000, 5270000, 2635000, 2635000),
  1710  				asserts.textArray("timezones", 4, []string{"CEST", "CET"}, []int64{2, 2}),
  1711  				asserts.pointingTo("inCountry", "Country"),
  1712  			},
  1713  		}
  1714  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
  1715  		expectedNoResultsAssertions := map[string][]assertFunc{}
  1716  
  1717  		testCases := []aggregateTestCase{
  1718  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
  1719  
  1720  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
  1721  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1722  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1723  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
  1724  
  1725  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
  1726  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1727  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1728  
  1729  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
  1730  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
  1731  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1732  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
  1733  		}
  1734  
  1735  		for _, tc := range testCases {
  1736  			query := aggregateCityQuery(tc.filters, "groupBy: [\"timezones\"]")
  1737  
  1738  			t.Run(tc.name, func(t *testing.T) {
  1739  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
  1740  				extracted := extractCityGroupByResult(result)
  1741  
  1742  				assert.Len(t, extracted, len(tc.groupedAssertions))
  1743  				for groupedBy, groupAssertions := range tc.groupedAssertions {
  1744  					group := findGroup(groupedBy, extracted)
  1745  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
  1746  
  1747  					for _, assertion := range groupAssertions {
  1748  						assertion(group)
  1749  					}
  1750  				}
  1751  			})
  1752  		}
  1753  	})
  1754  
  1755  	t.Run("aggregate City with group by museums", func(t *testing.T) {
  1756  		asserts := newAggregateResponseAssert(t)
  1757  		testCasesGen := &aggregateCityTestCases{}
  1758  
  1759  		expectedAllResultsAssertions := map[string][]assertFunc{
  1760  			"German Historical Museum": {
  1761  				asserts.groupedBy("German Historical Museum", "museums"),
  1762  				asserts.meta(1),
  1763  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1764  				asserts.date("cityRights", 1),
  1765  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1766  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1767  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1768  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1769  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1770  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1771  				asserts.pointingTo("inCountry", "Country"),
  1772  			},
  1773  			"Rijksmuseum": {
  1774  				asserts.groupedBy("Rijksmuseum", "museums"),
  1775  				asserts.meta(1),
  1776  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1777  				asserts.date("cityRights", 1),
  1778  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1779  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1780  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1781  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1782  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1783  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1784  				asserts.pointingTo("inCountry", "Country"),
  1785  			},
  1786  			"Stedelijk Museum": {
  1787  				asserts.groupedBy("Stedelijk Museum", "museums"),
  1788  				asserts.meta(1),
  1789  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1790  				asserts.date("cityRights", 1),
  1791  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1792  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1793  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1794  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1795  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1796  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1797  				asserts.pointingTo("inCountry", "Country"),
  1798  			},
  1799  			"Onomato": {
  1800  				asserts.groupedBy("Onomato", "museums"),
  1801  				asserts.meta(1),
  1802  				asserts.number("cityArea", 1, 217.22, 217.22, 217.22, 217.22, 217.22, 217.22),
  1803  				asserts.date("cityRights", 1),
  1804  				asserts.text("history", 1, []string{historyDusseldorf}, []int64{1}),
  1805  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1806  				asserts.textArray("museums", 3, []string{"Onomato", "Schiffahrt Museum", "Schlossturm"}, []int64{1, 1, 1}),
  1807  				asserts.text("name", 1, []string{"Dusseldorf"}, []int64{1}),
  1808  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1809  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1810  				asserts.pointingTo("inCountry", "Country"),
  1811  			},
  1812  			"Schiffahrt Museum": {
  1813  				asserts.groupedBy("Schiffahrt Museum", "museums"),
  1814  				asserts.meta(1),
  1815  				asserts.number("cityArea", 1, 217.22, 217.22, 217.22, 217.22, 217.22, 217.22),
  1816  				asserts.date("cityRights", 1),
  1817  				asserts.text("history", 1, []string{historyDusseldorf}, []int64{1}),
  1818  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1819  				asserts.textArray("museums", 3, []string{"Onomato", "Schiffahrt Museum", "Schlossturm"}, []int64{1, 1, 1}),
  1820  				asserts.text("name", 1, []string{"Dusseldorf"}, []int64{1}),
  1821  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1822  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1823  				asserts.pointingTo("inCountry", "Country"),
  1824  			},
  1825  			"Schlossturm": {
  1826  				asserts.groupedBy("Schlossturm", "museums"),
  1827  				asserts.meta(1),
  1828  				asserts.number("cityArea", 1, 217.22, 217.22, 217.22, 217.22, 217.22, 217.22),
  1829  				asserts.date("cityRights", 1),
  1830  				asserts.text("history", 1, []string{historyDusseldorf}, []int64{1}),
  1831  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1832  				asserts.textArray("museums", 3, []string{"Onomato", "Schiffahrt Museum", "Schlossturm"}, []int64{1, 1, 1}),
  1833  				asserts.text("name", 1, []string{"Dusseldorf"}, []int64{1}),
  1834  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1835  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1836  				asserts.pointingTo("inCountry", "Country"),
  1837  			},
  1838  			"Museum Boijmans Van Beuningen": {
  1839  				asserts.groupedBy("Museum Boijmans Van Beuningen", "museums"),
  1840  				asserts.meta(1),
  1841  				asserts.number("cityArea", 1, 319.35, 319.35, 319.35, 319.35, 319.35, 319.35),
  1842  				asserts.date("cityRights", 1),
  1843  				asserts.text("history", 1, []string{historyRotterdam}, []int64{1}),
  1844  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1845  				asserts.textArray("museums", 3, []string{"Museum Boijmans Van Beuningen", "Wereldmuseum", "Witte de With Center for Contemporary Art"}, []int64{1, 1, 1}),
  1846  				asserts.text("name", 1, []string{"Rotterdam"}, []int64{1}),
  1847  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1848  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1849  				asserts.pointingTo("inCountry", "Country"),
  1850  			},
  1851  			"Wereldmuseum": {
  1852  				asserts.groupedBy("Wereldmuseum", "museums"),
  1853  				asserts.meta(1),
  1854  				asserts.number("cityArea", 1, 319.35, 319.35, 319.35, 319.35, 319.35, 319.35),
  1855  				asserts.date("cityRights", 1),
  1856  				asserts.text("history", 1, []string{historyRotterdam}, []int64{1}),
  1857  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1858  				asserts.textArray("museums", 3, []string{"Museum Boijmans Van Beuningen", "Wereldmuseum", "Witte de With Center for Contemporary Art"}, []int64{1, 1, 1}),
  1859  				asserts.text("name", 1, []string{"Rotterdam"}, []int64{1}),
  1860  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1861  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1862  				asserts.pointingTo("inCountry", "Country"),
  1863  			},
  1864  			"Witte de With Center for Contemporary Art": {
  1865  				asserts.groupedBy("Witte de With Center for Contemporary Art", "museums"),
  1866  				asserts.meta(1),
  1867  				asserts.number("cityArea", 1, 319.35, 319.35, 319.35, 319.35, 319.35, 319.35),
  1868  				asserts.date("cityRights", 1),
  1869  				asserts.text("history", 1, []string{historyRotterdam}, []int64{1}),
  1870  				asserts.boolean("isCapital", 1, 1, 0, 1, 0),
  1871  				asserts.textArray("museums", 3, []string{"Museum Boijmans Van Beuningen", "Wereldmuseum", "Witte de With Center for Contemporary Art"}, []int64{1, 1, 1}),
  1872  				asserts.text("name", 1, []string{"Rotterdam"}, []int64{1}),
  1873  				asserts.int("population", 1, 600000, 600000, 600000, 600000, 600000, 600000),
  1874  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1875  				asserts.pointingTo("inCountry", "Country"),
  1876  			},
  1877  		}
  1878  		expectedResultsWithDataAssertions := map[string][]assertFunc{
  1879  			"German Historical Museum": {
  1880  				asserts.groupedBy("German Historical Museum", "museums"),
  1881  				asserts.meta(1),
  1882  				asserts.number("cityArea", 1, 891.96, 891.96, 891.96, 891.96, 891.96, 891.96),
  1883  				asserts.date("cityRights", 1),
  1884  				asserts.text("history", 1, []string{historyBerlin}, []int64{1}),
  1885  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1886  				asserts.textArray("museums", 1, []string{"German Historical Museum"}, []int64{1}),
  1887  				asserts.text("name", 1, []string{"Berlin"}, []int64{1}),
  1888  				asserts.int("population", 1, 3470000, 3470000, 3470000, 3470000, 3470000, 3470000),
  1889  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1890  				asserts.pointingTo("inCountry", "Country"),
  1891  			},
  1892  			"Rijksmuseum": {
  1893  				asserts.groupedBy("Rijksmuseum", "museums"),
  1894  				asserts.meta(1),
  1895  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1896  				asserts.date("cityRights", 1),
  1897  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1898  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1899  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1900  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1901  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1902  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1903  				asserts.pointingTo("inCountry", "Country"),
  1904  			},
  1905  			"Stedelijk Museum": {
  1906  				asserts.groupedBy("Stedelijk Museum", "museums"),
  1907  				asserts.meta(1),
  1908  				asserts.number("cityArea", 1, 891.95, 891.95, 891.95, 891.95, 891.95, 891.95),
  1909  				asserts.date("cityRights", 1),
  1910  				asserts.text("history", 1, []string{historyAmsterdam}, []int64{1}),
  1911  				asserts.boolean("isCapital", 1, 0, 1, 0, 1),
  1912  				asserts.textArray("museums", 2, []string{"Rijksmuseum", "Stedelijk Museum"}, []int64{1, 1}),
  1913  				asserts.text("name", 1, []string{"Amsterdam"}, []int64{1}),
  1914  				asserts.int("population", 1, 1800000, 1800000, 1800000, 1800000, 1800000, 1800000),
  1915  				asserts.textArray("timezones", 2, []string{"CEST", "CET"}, []int64{1, 1}),
  1916  				asserts.pointingTo("inCountry", "Country"),
  1917  			},
  1918  		}
  1919  		expectedResultsWithoutDataAssertions := map[string][]assertFunc{}
  1920  		expectedNoResultsAssertions := map[string][]assertFunc{}
  1921  
  1922  		testCases := []aggregateTestCase{
  1923  			testCasesGen.WithoutFilters(expectedAllResultsAssertions),
  1924  
  1925  			testCasesGen.WithWhereFilter_AllResults(expectedAllResultsAssertions),
  1926  			testCasesGen.WithWhereFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1927  			testCasesGen.WithWhereFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1928  			testCasesGen.WithWhereFilter_NoResults(expectedNoResultsAssertions),
  1929  
  1930  			testCasesGen.WithNearObjectFilter_AllResults(expectedAllResultsAssertions),
  1931  			testCasesGen.WithNearObjectFilter_ResultsWithData(expectedResultsWithDataAssertions),
  1932  			testCasesGen.WithNearObjectFilter_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1933  
  1934  			testCasesGen.WithWhereAndNearObjectFilters_AllResults(expectedAllResultsAssertions),
  1935  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithData(expectedResultsWithDataAssertions),
  1936  			testCasesGen.WithWhereAndNearObjectFilters_ResultsWithoutData(expectedResultsWithoutDataAssertions),
  1937  			testCasesGen.WithWhereAndNearObjectFilters_NoResults(expectedNoResultsAssertions),
  1938  		}
  1939  
  1940  		for _, tc := range testCases {
  1941  			query := aggregateCityQuery(tc.filters, "groupBy: [\"museums\"]")
  1942  
  1943  			t.Run(tc.name, func(t *testing.T) {
  1944  				result := graphqlhelper.AssertGraphQL(t, helper.RootAuth, query)
  1945  				extracted := extractCityGroupByResult(result)
  1946  
  1947  				assert.Len(t, extracted, len(tc.groupedAssertions))
  1948  				for groupedBy, groupAssertions := range tc.groupedAssertions {
  1949  					group := findGroup(groupedBy, extracted)
  1950  					require.NotNil(t, group, fmt.Sprintf("Group '%s' not found", groupedBy))
  1951  
  1952  					for _, assertion := range groupAssertions {
  1953  						assertion(group)
  1954  					}
  1955  				}
  1956  			})
  1957  		}
  1958  	})
  1959  }
  1960  
  1961  func extractArrayClassGroupByResult(result *graphqlhelper.GraphQLResult) []interface{} {
  1962  	return extractAggregateResult(result, arrayClassName)
  1963  }
  1964  
  1965  func extractDuplicatesClassGroupByResult(result *graphqlhelper.GraphQLResult) []interface{} {
  1966  	return extractAggregateResult(result, duplicatesClassName)
  1967  }
  1968  
  1969  func extractCityGroupByResult(result *graphqlhelper.GraphQLResult) []interface{} {
  1970  	return extractAggregateResult(result, cityClassName)
  1971  }
  1972  
  1973  func findGroup(groupedBy string, groups []interface{}) map[string]interface{} {
  1974  	for i := range groups {
  1975  		if group, ok := groups[i].(map[string]interface{}); !ok {
  1976  			continue
  1977  		} else if gb, exists := group["groupedBy"]; !exists {
  1978  			continue
  1979  		} else if gbm, ok := gb.(map[string]interface{}); !ok {
  1980  			continue
  1981  		} else if value, exists := gbm["value"]; !exists {
  1982  			continue
  1983  		} else if groupedByValue, ok := value.(string); !ok {
  1984  			continue
  1985  		} else if groupedByValue == groupedBy {
  1986  			return group
  1987  		}
  1988  	}
  1989  	return nil
  1990  }