示例#1
0
        public static IQueryable <T> ApplySortExpression <T>(this ISortOptions options, IQueryable <T> queryable)
        {
            if (string.IsNullOrEmpty(options.SortExpression))
            {
                return(queryable);
            }

            var type     = typeof(T);
            var property = type.GetTypeInfo().GetProperty(options.SortExpression);

            if (property == null)
            {
                throw new Exception($"Could not sort by property '{options.SortExpression}', since it does not exists.");
            }

            var parameter      = Expression.Parameter(type, "p");
            var propertyAccess = Expression.MakeMemberAccess(parameter, property);
            var orderBy        = Expression.Lambda(propertyAccess, parameter);

            var result = Expression.Call(typeof(Queryable),
                                         GetSortingMethodName(options),
                                         new[] { type, property.PropertyType },
                                         queryable.Expression,
                                         Expression.Quote(orderBy));

            return(queryable.Provider.CreateQuery <T>(result));
        }
        private static IOrderedQueryable <TModel> ApplyOptions <TModel>(
            this IQueryable <TModel> query, ISortOptions options)
            where TModel : IQueryModel
        {
            var propertySelectorExpression = ReflectionHelper
                                             .GetPropertySelectorExpressionFor <TModel, IComparable>(
                options.PropertyName);

            return(options.SortDirection == SortDirection.Ascending
                ? query.OrderBy(propertySelectorExpression)
                : query.OrderByDescending(propertySelectorExpression));
        }
        public static IQueryable <T> ApplySort <T>(this IQueryable <T> query, ISortOptions options)
        {
            if (options?.OrderBy?.Length > 0)
            {
                var _orderBy      = options.OrderBy;
                var orderByLength = _orderBy.Length;

                // get given type's properties
                var properties       = typeof(T).GetProperties();
                var propertiesLength = properties.Length;

                bool useThenBy = false;

                // iterate over all terms
                for (int i = 0; i < orderByLength; i++)
                {
                    // if invalid term then skip it
                    if (string.IsNullOrEmpty(_orderBy[i]))
                    {
                        continue;
                    }

                    var tokens = _orderBy[i].Split(' ');
                    if (tokens.Length != 0)
                    {
                        for (int j = 0; j < propertiesLength; j++)
                        {
                            // if property has sortable attribute and sort term equals to property name
                            bool hasSortableAttribute = properties[j].GetCustomAttributes <SortableAttribute>().Count() > 0 && properties[j].Name.Equals(tokens[0], StringComparison.OrdinalIgnoreCase);

                            if (hasSortableAttribute)
                            {
                                bool decending = tokens.Length > 1 && tokens[1].Equals(decendingString, StringComparison.OrdinalIgnoreCase);

                                // build expression query
                                var property  = ExpressionUtilities.GetPropertyInfo <T>(properties[j].Name);
                                var parameter = ExpressionUtilities.Parameter <T>();
                                var key       = ExpressionUtilities.GetPropertyExpression(parameter, property);
                                var lambda    = ExpressionUtilities.GetLambda(typeof(T), property.PropertyType, parameter, key);

                                // query.OrderBy/ThenBy[Decending](x => x.Property)
                                query     = ExpressionUtilities.CallOrderByOrThenBy(query, useThenBy, decending, property.PropertyType, lambda);
                                useThenBy = true;
                                break;
                            }
                        }
                    }
                }
            }
            return(query);
        }
示例#4
0
        /// <summary>
        /// Performs a search using the specified <paramref name="sortOptions"/>.
        /// </summary>
        /// <param name="operation">The boolean operation the search should be based on.</param>
        /// <param name="sortOptions">The sort options specyfing how the results should be sorted.</param>
        /// <param name="results">The results of the search.</param>
        /// <param name="total">The total amount of results returned by the search.</param>
        protected virtual void Execute(IBooleanOperation operation, ISortOptions sortOptions, out IEnumerable <ISearchResult> results, out long total)
        {
            // Cast the boolean operation to IQueryExecutor
            IQueryExecutor executor = operation;

            // If "SortField" doesn't specified, we don't apply any sorting
            if (!string.IsNullOrWhiteSpace(sortOptions.SortField))
            {
                switch (sortOptions.SortOrder)
                {
                case SortOrder.Ascending:
                    executor = operation.OrderBy(new SortableField(sortOptions.SortField, sortOptions.SortType));
                    break;

                case SortOrder.Descending:
                    executor = operation.OrderByDescending(new SortableField(sortOptions.SortField, sortOptions.SortType));
                    break;

                default:
                    throw new Exception($"Unsupported sort order: {sortOptions.SortOrder}");
                }
            }

            if (sortOptions is IOffsetOptions offset)
            {
                ISearchResults allResults = executor.Execute();

                // Update the total amount of results
                total = allResults.TotalItemCount;

                // Apply limit and offset
                results = allResults
                          .Skip(offset.Offset)
                          .Take(offset.Limit);
            }
            else
            {
                // Since no offset or limit is specified, we request all results
                ISearchResults allResults = executor.Execute(int.MaxValue);

                // Update the total amount of results
                total = allResults.TotalItemCount;

                // Update "results" with the value of "allResults" as we're not filtering the results
                results = allResults;
            }
        }
示例#5
0
 private static string GetSortingMethodName(ISortOptions options)
 {
     return(options.SortDescending ? "OrderByDescending" : "OrderBy");
 }