Inheritance: DataSourceLoadOptionsBase
        public void AllKeys() {
            var opts = new SampleLoadOptions();
            var values = new Dictionary<string, string> {
                { DataSourceLoadOptionsParser.KEY_IS_COUNT_QUERY, "true" },
                { DataSourceLoadOptionsParser.KEY_REQUIRE_TOTAL_COUNT, "true" },
                { DataSourceLoadOptionsParser.KEY_REQUIRE_GROUP_COUNT, "true" },
                { DataSourceLoadOptionsParser.KEY_SKIP, "42" },
                { DataSourceLoadOptionsParser.KEY_TAKE, "43" },
                { DataSourceLoadOptionsParser.KEY_SORT, @"[ { ""selector"": ""foo"", ""desc"": true } ]" },
                { DataSourceLoadOptionsParser.KEY_GROUP, @"[ { ""selector"": ""g"" } ]" },
                { DataSourceLoadOptionsParser.KEY_FILTER, @" [ ""foo"", ""bar"" ] " },
                { DataSourceLoadOptionsParser.KEY_TOTAL_SUMMARY, @"[ { ""selector"": ""total"", ""summaryType"": ""min"" } ]" },
                { DataSourceLoadOptionsParser.KEY_GROUP_SUMMARY, @"[ { ""selector"": ""group"", ""summaryType"": ""max"" } ]" }
            };

            DataSourceLoadOptionsParser.Parse(opts, key => values[key]);

            Assert.True(opts.IsCountQuery);
            Assert.True(opts.RequireTotalCount);
            Assert.True(opts.RequireGroupCount);
            Assert.Equal(42, opts.Skip);
            Assert.Equal(43, opts.Take);
            Assert.Equal("foo", opts.Sort[0].Selector);
            Assert.True(opts.Sort[0].Desc);
            Assert.Equal("g", opts.Group[0].Selector);
            Assert.Equal(new[] { "foo", "bar" }, opts.Filter.Cast<string>());

            Assert.Equal("total", opts.TotalSummary[0].Selector);
            Assert.Equal("min", opts.TotalSummary[0].SummaryType);

            Assert.Equal("group", opts.GroupSummary[0].Selector);
            Assert.Equal("max", opts.GroupSummary[0].SummaryType);
        }
Example #2
0
        public void RequireGroupCount()
        {
            var data = new[] {
                new { G = 1 },
                new { G = 1 },
                new { G = 2 },
                new { G = 2 }
            };

            var loadOptions = new SampleLoadOptions {
                RemoteGrouping    = true,
                RequireTotalCount = true,
                RequireGroupCount = true,
                Skip  = 0,
                Take  = 1,
                Group = new[] {
                    new GroupingInfo {
                        Selector = "G", IsExpanded = false
                    }
                }
            };

            var result = DataSourceLoader.Load(data, loadOptions);

            Assert.Equal(4, result.totalCount);

            var groups = result.data.Cast <Group>().ToArray();

            Assert.Single(groups);
            Assert.Equal(2, result.groupCount);
        }
Example #3
0
        public void Summary_MissingOverload_SumBrute()
        {
            var values = new[] {
                new {
                    p1 = byte.MaxValue,
                    p2 = sbyte.MaxValue,
                    p3 = short.MaxValue,
                    p4 = ushort.MaxValue,
                    p5 = uint.MaxValue,
                    p6 = ulong.MaxValue
                }
            };

            var nullableValues = new[] {
                new {
                    p1 = new byte?(byte.MaxValue),
                    p2 = new sbyte?(sbyte.MaxValue),
                    p3 = new short?(short.MaxValue),
                    p4 = new ushort?(ushort.MaxValue),
                    p5 = new uint?(uint.MaxValue),
                    p6 = new ulong?(ulong.MaxValue)
                }
            };

            var nulls = new[] {
                new {
                    p1 = new byte?(),
                    p2 = new sbyte?(),
                    p3 = new short?(),
                    p4 = new ushort?(),
                    p5 = new uint?(),
                    p6 = new ulong?()
                }
            };

            var valuesExpectation = new object[] {
                (decimal)byte.MaxValue,
                (decimal)sbyte.MaxValue,
                (decimal)short.MaxValue,
                (decimal)ushort.MaxValue,
                (decimal)uint.MaxValue,
                (decimal)ulong.MaxValue,
            };

            var nullsExpectation = new object[] { 0m, 0m, 0m, 0m, 0m, 0m };

            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                TotalSummary   = Enumerable.Range(1, 6)
                                 .Select(i => new SummaryInfo {
                    Selector = "p" + i, SummaryType = "sum"
                })
                                 .ToArray()
            };

            Assert.Equal(valuesExpectation, DataSourceLoader.Load(values, loadOptions).summary);
            Assert.Equal(valuesExpectation, DataSourceLoader.Load(nullableValues, loadOptions).summary);
            Assert.Equal(nullsExpectation, DataSourceLoader.Load(nulls, loadOptions).summary);
        }
Example #4
0
        public void CustomSorting()
        {
            try {
                CustomSortCompilers.RegisterBinaryExpressionCompiler((target, info) => {
                    if (info.AccessorText == "Name")
                    {
                        var prop = Expression.Property(info.DataItemExpression, nameof(Product.Name));

                        var body1 = Expression.Condition(Expression.Equal(prop, Expression.Constant("Lightsaber")), Expression.Constant(1), Expression.Constant(2));
                        var expr1 = Expression.Lambda(body1, (ParameterExpression)info.DataItemExpression);
                        var expr2 = Expression.Lambda(prop, (ParameterExpression)info.DataItemExpression);

                        target = Expression.Call(typeof(Queryable), Utils.GetSortMethod(info.First, info.Desc),
                                                 new[] { info.DataItemExpression.Type, expr1.ReturnType }, target, Expression.Quote(expr1));
                        target = Expression.Call(typeof(Queryable), Utils.GetSortMethod(false, info.Desc),
                                                 new[] { info.DataItemExpression.Type, expr2.ReturnType }, target, Expression.Quote(expr2));

                        return(target);
                    }

                    return(null);
                });

                var source = new[] {
                    new Product {
                        Name = "Box", Price = 5
                    },
                    new Product {
                        Name = "Pen", Price = 2
                    },
                    new Product {
                        Name = "Bike", Price = 2000
                    },
                    new Product {
                        Name = "Lightsaber", Price = 5000000
                    }
                };


                var loadOptions = new SampleLoadOptions {
                    Sort = new[] { new SortingInfo {
                                       Selector = "Name", Desc = false
                                   } },
                    RequireTotalCount = true
                };

                var loadResult = DataSourceLoader.Load(source, loadOptions);
                var data       = loadResult.data.Cast <Product>().ToArray();
                Assert.Equal("Lightsaber", data[0].Name);
                Assert.Equal("Bike", data[1].Name);
                Assert.Equal("Box", data[2].Name);
                Assert.Equal("Pen", data[3].Name);
            } finally {
                CustomSortCompilers.Sort.CompilerFuncs.Clear();
            }
        }
        public void TotalCount() {
            var data = new[] { 1, 3, 2 };
            var options = new SampleLoadOptions {
                Filter = new object[] { "this", "<>", 2 },
                Take = 1,
                IsCountQuery = true
            };

            Assert.Equal(2, DataSourceLoader.Load(data, options));
        }
        public void MustNotParseDates() {
            var opts = new SampleLoadOptions();

            DataSourceLoadOptionsParser.Parse(opts, key => {
                if(key == DataSourceLoadOptionsParser.KEY_FILTER)
                    return @"[ ""d"", ""2011-12-13T14:15:16Z"" ]";
                return null;
            });

            Assert.IsType<string>(opts.Filter[1]);
        }
Example #7
0
        public void TotalCount()
        {
            var data    = new[] { 1, 3, 2 };
            var options = new SampleLoadOptions {
                Filter       = new object[] { "this", "<>", 2 },
                Take         = 1,
                IsCountQuery = true
            };

            Assert.Equal(2, DataSourceLoader.Load(data, options).totalCount);
        }
Example #8
0
 public void GlobalSwitch()
 {
     StaticBarrier.Run(delegate {
         var options = new SampleLoadOptions {
             Filter = new[] { "this", "contains", "A" }
         };
         DataSourceLoadOptionsBase.StringToLowerDefault = false;
         DataSourceLoader.Load(new[] { "" }, options).data.Cast <object>().ToArray();
         Assert.DoesNotContain(options.ExpressionLog, line => line.Contains("ToLower"));
     });
 }
        public static void Run <T>(IQueryable <T> data) where T : IEntity
        {
            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                Group          = BuildGroupParams(),
                GroupSummary   = BuildSummaryParams(Compat.CanUseRemoteAvg(data.Provider))
            };

            Assert.Null(Record.Exception(delegate {
                DataSourceLoader.Load(data, loadOptions);
            }));
        }
        public void RemoteSelectFalse()
        {
            var options = new SampleLoadOptions {
                Select       = new[] { "abc" },
                RemoteSelect = false
            };

            Assert.Equal(
                "data",
                Compat.CreateDataSourceExpressionBuilder <object>(options, false).BuildLoadExpr().ToString()
                );
        }
Example #11
0
        public void DisabledWithoutTake()
        {
            var loadOptions = new SampleLoadOptions {
                SuppressGuardNulls    = true,
                PaginateViaPrimaryKey = true
            };

            DataSourceLoader.Load(new object[0], loadOptions);

            Assert.NotEmpty(loadOptions.ExpressionLog);
            Assert.DoesNotContain(loadOptions.ExpressionLog, line => line.Contains(".Select"));
        }
        public static void Run <T>(IQueryable <T> data) where T : IEntity
        {
            var group = Array.ConvertAll(
                new[] { nameof(IEntity.Group1), nameof(IEntity.Group2) },
                i => new GroupingInfo {
                Selector   = i,
                IsExpanded = false
            }
                );

            var summary = Array.ConvertAll(
                new[] { "count", "min", "max", "sum", "avg" },
                i => new SummaryInfo {
                Selector    = nameof(IEntity.Value),
                SummaryType = i
            }
                );

            var loadOptions = new SampleLoadOptions {
                Group        = group,
                GroupSummary = summary,
                TotalSummary = summary
            };

            {
                var loadResult = DataSourceLoader.Load(data, loadOptions);
                var rootItems  = (IList <Group>)loadResult.data;

                var group_A = rootItems[0];
                var group_B = rootItems[1];

                var group_A_A = (Group)group_A.items[0];
                var group_A_B = (Group)group_A.items[1];
                var group_B_A = (Group)group_B.items[0];

                Assert.Equal(new object[] { 4, 1, 5, 9m, 3m }, group_A.summary);
                Assert.Equal(new object[] { 2, 1, 1, 1m, 1m }, group_A_A.summary);
                Assert.Equal(new object[] { 2, 3, 5, 8m, 4m }, group_A_B.summary);

                Assert.Equal(new object[] { 1, null, null, 0m, null }, group_B.summary);
                Assert.Equal(new object[] { 1, null, null, 0m, null }, group_B_A.summary);

                Assert.Equal(new object[] { 5, 1, 5, 9m, 3m }, loadResult.summary);
            }

            loadOptions.Filter = new[] { nameof(IEntity.Group1), "nonexistent" };

            {
                var loadResult = DataSourceLoader.Load(data, loadOptions);
                Assert.Equal(new object[] { 0, null, null, 0m, null }, loadResult.summary);
            }
        }
        static void TestFilter <T>(IEnumerable <T> source, string operation, T operand, string expectedExprPart)
        {
            var loadOptions = new SampleLoadOptions {
                GuardNulls   = false,
                Filter       = new object[] { "this", operation, operand },
                IsCountQuery = true
            };

            var loadResult = DataSourceLoader.Load(source, loadOptions);

            Assert.Equal(1, loadResult.totalCount);
            Assert.Contains(expectedExprPart, loadOptions.ExpressionLog[0]);
        }
        public void AlwaysOrderDataByPrimaryKey()
        {
            var options = new SampleLoadOptions {
                PrimaryKey = new[] { "Item2", "Item1" }
            };

            var builder = new DataSourceExpressionBuilder <Tuple <int, int> >(options, false);

            Assert.Equal(
                "data.OrderBy(obj => obj.Item2).ThenBy(obj => obj.Item1)",
                builder.BuildLoadExpr().Body.ToString()
                );
        }
        public void L2O_Select_Null()
        {
            var data = new string[] { null };

            var loadOptions = new SampleLoadOptions {
                Select = new[] { "Length" }
            };

            var loadResult = DataSourceLoader.Load(data, loadOptions);
            var items      = loadResult.data.Cast <IDictionary <string, object> >();

            Assert.Null(items.First()["Length"]);
        }
        public void Load_NoRequireTotalCount() {
            var data = new[] { 1, 3, 5, 2, 4 };
            var options = new SampleLoadOptions {
                Skip = 1,
                Take = 2,
                Filter = new object[] { "this", "<>", 2 },
                Sort = new[] {
                    new SortingInfo { Selector = "this" }
                },
                RequireTotalCount = false
            };

            Assert.Equal(new[] { 3, 4 }, DataSourceLoader.Load(data, options) as IEnumerable<int>);
        }
        public void Load_PreSelect_CI()
        {
            // https://github.com/DevExpress/DevExtreme.AspNet.Data/pull/400

            var loadOptions = new SampleLoadOptions {
                Select    = new[] { "prop" },
                PreSelect = new[] { "Prop" }
            };

            var loadResult = DataSourceLoader.Load(new[] { new { Prop = 123 } }, loadOptions);
            var items      = loadResult.data.Cast <IDictionary <string, object> >().ToArray();

            Assert.Equal(123, items.First()["Prop"]);
        }
        public void MustNotParseDates()
        {
            var opts = new SampleLoadOptions();

            DataSourceLoadOptionsParser.Parse(opts, key => {
                if (key == DataSourceLoadOptionsParser.KEY_FILTER)
                {
                    return(@"[ ""d"", ""2011-12-13T14:15:16Z"" ]");
                }
                return(null);
            });

            Assert.IsType <string>(opts.Filter[1]);
        }
        public void NotUsedWoSkip()
        {
            var loadOptions = new SampleLoadOptions {
                PaginateViaPrimaryKey = true,
                Take = 123
            };

            DataSourceLoader.Load(new object[0], loadOptions);

            Assert.All(
                loadOptions.ExpressionLog,
                i => Assert.DoesNotContain(".Select(", i)
                );
        }
        public void GlobalSwitch()
        {
            var origStringToLowerDefault = DataSourceLoadOptionsBase.StringToLowerDefault;

            try {
                var options = new SampleLoadOptions {
                    Filter = new[] { "this", "contains", "A" }
                };
                DataSourceLoadOptionsBase.StringToLowerDefault = false;
                DataSourceLoader.Load(new[] { "" }, options).data.Cast <object>().ToArray();
                Assert.DoesNotContain(options.ExpressionLog, line => line.Contains("ToLower"));
            } finally {
                DataSourceLoadOptionsBase.StringToLowerDefault = origStringToLowerDefault;
            }
        }
Example #21
0
        public void GroupSummary_NoGroups()
        {
            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                GroupSummary   = new[] {
                    new SummaryInfo {
                        Selector = "any"
                    }
                }
            };

            DataSourceLoader.Load(new object[0], loadOptions);

            Assert.DoesNotContain(loadOptions.ExpressionLog, line => line.Contains("GroupBy"));
        }
Example #22
0
        public void Load_Select()
        {
            var data = new[] {
                new { f1 = 1, f2 = 2 }
            };

            var loadOptions = new SampleLoadOptions {
                Select = new[] { "f2" }
            };

            var item = DataSourceLoader.Load(data, loadOptions).data.Cast <IDictionary>().First();

            Assert.Equal(1, item.Keys.Count);
            Assert.Equal(2, item["f2"]);
        }
        public void Issue477(DateParseHandling dateParseHandling)
        {
            var date               = new DateTimeOffset(2021, 1, 1, 0, 0, 0, TimeSpan.Zero);
            var filterJSON         = JsonConvert.SerializeObject(new object[] { "this", date });
            var deserializedFilter = JsonConvert.DeserializeObject <IList>(filterJSON, new JsonSerializerSettings {
                DateParseHandling = dateParseHandling
            });

            var loadOptions = new SampleLoadOptions {
                Filter = deserializedFilter
            };

            var loadResult = DataSourceLoader.Load(new[] { date }, loadOptions);

            Assert.Single(loadResult.data);
        }
        public void L2O_NullVsDefault_Filter()
        {
            var data = new[] {
                null,
                ""
            };

            var loadOptions = new SampleLoadOptions {
                Filter = new[] { "Length", "0" }
            };

            var loadResult = DataSourceLoader.Load(data, loadOptions);
            var items      = loadResult.data.Cast <string>().ToArray();

            Assert.Single(items);
        }
        public void ArrayContainsWithNullGuard()
        {
            try {
                CustomFilterCompilers.RegisterBinaryExpressionCompiler(info => {
                    if (info.DataItemExpression.Type == typeof(Post) && info.AccessorText == "Tags" && info.Operation == "contains")
                    {
                        var text = Convert.ToString(info.Value);

                        var tagsAccessor = Expression.Property(info.DataItemExpression, "Tags");

                        var containsCall = Expression.Call(
                            typeof(Enumerable), nameof(Enumerable.Contains), new[] { typeof(string) },
                            tagsAccessor, Expression.Constant(text) /*, Expression.Constant(StringComparer.InvariantCultureIgnoreCase)*/
                            );

                        return(Expression.Condition(
                                   Expression.MakeBinary(ExpressionType.NotEqual, tagsAccessor, Expression.Constant(null, typeof(string[]))),
                                   containsCall,
                                   Expression.Constant(false)
                                   ));
                    }

                    return(null);
                });

                var source = new[] {
                    new Post {
                        Tags = new[] { "news", "article" }
                    },
                    new Post {
                        Tags = new[] { "announcement" }
                    }
                };

                var loadOptions = new SampleLoadOptions {
                    Filter            = new[] { "Tags", "contains", "news" },
                    RequireTotalCount = true
                };

                var loadResult = DataSourceLoader.Load(source, loadOptions);
                Assert.Equal(1, loadResult.totalCount);
                Assert.Contains(loadOptions.ExpressionLog, line => line.Contains(@".Where(obj => IIF((obj.Tags != null), obj.Tags.Contains(""news""), False))"));
            } finally {
                CustomFilterCompilers.Binary.CompilerFuncs.Clear();
            }
        }
Example #26
0
        public void Load_NoRequireTotalCount()
        {
            var data    = new[] { 1, 3, 5, 2, 4 };
            var options = new SampleLoadOptions {
                Skip   = 1,
                Take   = 2,
                Filter = new object[] { "this", "<>", 2 },
                Sort   = new[] {
                    new SortingInfo {
                        Selector = "this"
                    }
                },
                RequireTotalCount = false
            };

            Assert.Equal(new[] { 3, 4 }, DataSourceLoader.Load(data, options).data.Cast <int>());
        }
        public void Load_RequireTotalCount() {
            var data = new[] { 1, 3, 5, 2, 4 };
            var options = new SampleLoadOptions {
                Skip = 1,
                Take = 2,
                Filter = new object[] { "this", "<>", 2 },
                Sort = new[] {
                    new SortingInfo { Selector = "this" }
                },
                RequireTotalCount = true
            };

            var result = (DataSourceLoadResult)DataSourceLoader.Load(data, options);

            Assert.Equal(4, result.totalCount);
            Assert.Equal(new[] { 3, 4 }, result.data.Cast<int>());
        }
        public void Load_GridFilter_T616169()
        {
            var loadOptions = new SampleLoadOptions {
                Filter = new object[] {
                    new object[] { "f", ">", 0 },
                    "or",
                    new object[] { "f", "=", null }
                }
            };

            var data = new[] {
                new { f = 1 }
            };

            var loadResult = DataSourceLoader.Load(data, loadOptions);

            Assert.NotEmpty(loadResult.data);
        }
Example #29
0
        public void Load_SelectWithPaging()
        {
            var data = new[] {
                new { f = 1 },
                new { f = 2 }
            };

            var loadOptions = new SampleLoadOptions {
                Select = new[] { "f" },
                Skip   = 1,
                Take   = 1
            };

            var x = Record.Exception(delegate {
                DataSourceLoader.Load(data, loadOptions);
            });

            Assert.Null(x);
        }
Example #30
0
        public void ActiveForFirstPage()
        {
            var data = new[] {
                new { ID = 123 }
            };

            var loadOptions = new SampleLoadOptions {
                SuppressGuardNulls    = true,
                PrimaryKey            = new[] { "ID" },
                PaginateViaPrimaryKey = true,

                Skip = 0,
                Take = 123
            };

            DataSourceLoader.Load(data, loadOptions);

            Assert.Contains(".Select(obj => new AnonType`1", loadOptions.ExpressionLog[0]);
        }
Example #31
0
        public static IList <Group> Run <T>(IQueryable <T> data) where T : IEntity
        {
            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                Group          = BuildGroupParams(),
                GroupSummary   = BuildSummaryParams()
            };

            if (data.Provider.GetType().Name == "XPQuery`1")
            {
                // TODO
                // Temporary disabled due to NotSupportedException in PropertyAlias
                loadOptions.GroupSummary = loadOptions.GroupSummary
                                           .Where(i => i.SummaryType != "avg")
                                           .ToArray();
            }

            return((IList <Group>)DataSourceLoader.Load(data, loadOptions).data);
        }
Example #32
0
        public void Load_SelectNested(bool remoteSelect)
        {
            var data = new[] {
                new {
                    Name    = "Alex",
                    Address = new {
                        Zip    = "89104",
                        Street = new {
                            Line1 = "2000 S Las Vegas Blvd",
                            Line2 = ""
                        },
                        City = "Las Vegas"
                    },
                    Contacts = new {
                        Phone = "phone",
                        Email = "email"
                    },
                    Waste = ""
                }
            };

            var loadOptions = new SampleLoadOptions {
                Select       = new[] { "Name", "Address.City", "Address.Street.Line1", "Contacts.Email" },
                RemoteSelect = remoteSelect
            };

            var item = DataSourceLoader.Load(data, loadOptions).data.Cast <IDictionary <string, object> >().First();

            var address       = (IDictionary <string, object>)item["Address"];
            var addressStreet = (IDictionary <string, object>)address["Street"];
            var contacts      = (IDictionary <string, object>)item["Contacts"];

            Assert.Equal(3, item.Keys.Count);
            Assert.Equal(2, address.Keys.Count);
            Assert.Equal(1, addressStreet.Keys.Count);
            Assert.Equal(1, contacts.Keys.Count);

            Assert.Equal(data[0].Name, item["Name"]);
            Assert.Equal(data[0].Address.City, address["City"]);
            Assert.Equal(data[0].Address.Street.Line1, addressStreet["Line1"]);
            Assert.Equal(data[0].Contacts.Email, contacts["Email"]);
        }
Example #33
0
        public void Filter()
        {
            var loadOptions = new SampleLoadOptions {
                Filter = new object[] { P1, ">", 1 }
            };

            var data = new[] {
                CreateExpando(1m),
                CreateExpando(2d)
            };

            var objectResult  = ToDictArray(DataSourceLoader.Load <object>(data, loadOptions).data);
            var expandoResult = ToDictArray(DataSourceLoader.Load <ExpandoObject>(data, loadOptions).data);

            Assert.Single(objectResult);
            Assert.Equal(2d, objectResult[0][P1]);

            Assert.Single(expandoResult);
            Assert.Equal(2d, expandoResult[0][P1]);
        }
Example #34
0
        public static void Run <T>(IQueryable <T> data) where T : IEntity
        {
            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                Group          = BuildGroupParams(),
                GroupSummary   = BuildSummaryParams()
            };

            #warning Remove with https://github.com/aspnet/EntityFrameworkCore/issues/11711 fix
            if (data.Provider.GetType().FullName.StartsWith("Microsoft.EntityFrameworkCore"))
            {
                loadOptions.GroupSummary = loadOptions.GroupSummary
                                           .Where(i => i.SummaryType != "avg")
                                           .ToArray();
            }

            Assert.Null(Record.Exception(delegate {
                DataSourceLoader.Load(data, loadOptions);
            }));
        }
        public void PR202()
        {
            // https://github.com/DevExpress/DevExtreme.AspNet.Data/pull/202

            var options = new SampleLoadOptions {
                DefaultSort = "item1",
                Sort        = new[] {
                    new SortingInfo {
                        Selector = "ITEM1"
                    }
                }
            };

            var builder = Compat.CreateDataSourceExpressionBuilder <Tuple <int> >(options, false);

            Assert.Equal(
                "data.OrderBy(obj => obj.Item1)",
                builder.BuildLoadExpr().ToString()
                );
        }
        public void TotalSummaryOnly() {
            var data = new[] {
                new { a = 1 },
                new { a = 2 },
                new { a = 3 }
            };

            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                RequireTotalCount = true,
                Filter = new[] { "a", "<>", "2" },
                TotalSummary = new[] {
                    new SummaryInfo { Selector = "a", SummaryType = "sum" }
                },
                Skip = 1,
                Take = 1
            };

            var result = (DataSourceLoadResult)DataSourceLoader.Load(data, loadOptions);

            Assert.Equal(2, loadOptions.ExpressionLog.Count);

            // 1 - load paged data
            Assert.Contains("Skip", loadOptions.ExpressionLog[0]);
            Assert.Contains("Take", loadOptions.ExpressionLog[0]);

            // 2 - load summaries
            Assert.Contains("RemoteGroupKey`8()", loadOptions.ExpressionLog[1]);

            Assert.Equal(4M, result.summary[0]);
            Assert.Equal(1, result.data.Cast<object>().Count());
            Assert.Equal(2, result.totalCount);
        }
        public void RequireGroupCount() {
            var data = new[] {
                new { G = 1 },
                new { G = 1 },
                new { G = 2 },
                new { G = 2 }
            };

            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                RequireTotalCount = true,
                RequireGroupCount = true,
                Skip = 0,
                Take = 1,
                Group = new[] {
                    new GroupingInfo { Selector = "G", IsExpanded = false }
                }
            };

            var result = (DataSourceLoadResult)DataSourceLoader.Load(data, loadOptions);
            
            Assert.Equal(4, result.totalCount);

            var groups = result.data.Cast<Group>().ToArray();

            Assert.Equal(1, groups.Count());
            Assert.Equal(2, result.groupCount);
        }
        public void RequireGroupCountWhenGroupsAreExpanded() {
            var data = new[] {
                new { a = 1 },
                new { a = 2 },
                new { a = 2 }
            };

            var loadOptions = new SampleLoadOptions {
                RequireGroupCount = true,
                Group = new[] {
                    new GroupingInfo { Selector = "a", IsExpanded = true }
                },
                Skip = 1,
                Take = 1
            };

            var result = (DataSourceLoadResult)DataSourceLoader.Load(data, loadOptions);

            Assert.Equal(2, result.groupCount);
        }
        public void GroupingAndSummary() {
            /*

                G1=1
                    G2=1
                        A=1 B=1
                        A=2 B=3

                        count=2 sum(A)=3 avg(A)=1.5

                    G2=2
                        A=3 B=5

                        count=1 sum(A)=3 avg(A)=3

                    count=3 sum(A)=6 avg(A)=2

                G2=2
                    G1=1
                        A=4 B=7
                        A=5 B=9

                        count=2 sum(A)=9 avg(A)=4.5

                    G1=2
                        A=6 B=11

                        count=1 sum(A)=6 avg(A)=6

                    count=3 sum(A)=15, avg(A)=5

                count=6 sum(B)=36 avg(B)=6


            */


            var data = new[] {
                new { G1 = 1, G2 = 1, A = 1, B = 1 },
                new { G1 = 1, G2 = 1, A = 2, B = 3 },
                new { G1 = 1, G2 = 2, A = 3, B = 5 },
                new { G1 = 2, G2 = 1, A = 4, B = 7 },
                new { G1 = 2, G2 = 1, A = 5, B = 9 },
                new { G1 = 2, G2 = 2, A = 6, B = 11 },
            };

            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                RequireTotalCount = true,
                Group = new[] {
                    new GroupingInfo { Selector = "G1", IsExpanded = false },
                    new GroupingInfo { Selector = "G2", IsExpanded = false }
                },
                GroupSummary = new[] {
                    new SummaryInfo { SummaryType = "count" },
                    new SummaryInfo { Selector = "A", SummaryType = "sum" },
                    new SummaryInfo { Selector = "A", SummaryType = "avg" }
                },
                TotalSummary = new[] {
                    new SummaryInfo { SummaryType = "count" },
                    new SummaryInfo { Selector = "B", SummaryType = "sum" },
                    new SummaryInfo { Selector = "B", SummaryType = "avg" },                    
                }
            };

            var result = (DataSourceLoadResult)DataSourceLoader.Load(data, loadOptions);

            Assert.Equal(1, loadOptions.ExpressionLog.Count);
            Assert.Contains("RemoteGroupKey`8(K0 = obj.G1, K1 = obj.G2)", loadOptions.ExpressionLog[0]);

            Assert.Equal(new object[] { 6, 36M, 6M }, result.summary);
            Assert.Equal(6, result.totalCount);
            Assert.Equal(-1, result.groupCount);

            var groups = result.data.Cast<Group>().ToArray();

            var g1 = groups[0];
            var g2 = groups[1];
            var g11 = g1.items[0] as Group;
            var g12 = g1.items[1] as Group;
            var g21 = g2.items[0] as Group;
            var g22 = g2.items[1] as Group;

            Assert.Equal(1, g1.key);
            Assert.Equal(1, g11.key);
            Assert.Equal(2, g12.key);
            Assert.Equal(2, g2.key);
            Assert.Equal(1, g21.key);
            Assert.Equal(2, g22.key);

            Assert.Equal(new object[] { 3, 6M, 2M }, g1.summary);
            Assert.Equal(new object[] { 2, 3M, 1.5M }, g11.summary);
            Assert.Equal(new object[] { 1, 3M, 3M }, g12.summary);
            Assert.Equal(new object[] { 3, 15M, 5M }, g2.summary);
            Assert.Equal(new object[] { 2, 9M, 4.5M }, g21.summary);
            Assert.Equal(new object[] { 1, 6M, 6M }, g22.summary);
            
            Assert.Equal(2, g11.count);
            Assert.Equal(1, g12.count);            
            Assert.Equal(2, g21.count);
            Assert.Equal(1, g22.count);

            Assert.Null(g11.items);
            Assert.Null(g12.items);
            Assert.Null(g21.items);
            Assert.Null(g22.items);
        }
        public void NotUsedIfTotalCountOnly() {
            var data = new[] {
                new { a = 1 },
                new { a = 2 },
                new { a = 3 }
            };

            var loadOptions = new SampleLoadOptions {
                RemoteGrouping = true,
                RequireTotalCount = true,
                Filter = new[] { "a", "<>", "2" },
                Skip = 1,
                Take = 1
            };

            var result = (DataSourceLoadResult)DataSourceLoader.Load(data, loadOptions);

            Assert.False(loadOptions.ExpressionLog.Any(i => i.Contains("RemoteGroupKey")));

            Assert.Equal(2, result.totalCount);
            Assert.Null(result.summary);
            Assert.Equal(-1, result.groupCount);
        }