After a good dose of Googling and trying some things and not finding/getting the desired result I decided to post this question.
I have a custom made OrderBy
extension method and now when performing the OrderBy
operation I'd like to pass an AlphanumComparator
like this:
return divergences.OrderBy(sort, new AlphanumComparator());
Here's the extension method:
public static IQueryable<T> OrderBy<T>(this IQueryable<T> collection,
GridSortOptions sortOptions, AlphanumComparator comparer = null)
{
if (string.IsNullOrEmpty(sortOptions.Column))
{
return collection;
}
Type collectionType = typeof(T);
ParameterExpression parameterExpression = Expression.Parameter(collectionType, "p");
Expression seedExpression = parameterExpression;
Expression aggregateExpression = sortOptions.Column.Split('.').Aggregate(seedExpression, Expression.Property);
MemberExpression memberExpression = aggregateExpression as MemberExpression;
if (memberExpression == null)
{
throw new NullReferenceException(string.Format("Unable to cast Member Expression for given path: {0}.", sortOptions.Column));
}
LambdaExpression orderByExp = Expression.Lambda(memberExpression, parameterExpression);
const string orderBy = "OrderBy";
const string orderByDesc = "OrderByDescending";
Type childPropertyType = ((PropertyInfo)(memberExpression.Member)).PropertyType;
string methodToInvoke = sortOptions.Direction == MvcContrib.Sorting.SortDirection.Ascending ? orderBy : orderByDesc;
MethodCallExpression orderByCall;
orderByCall = Expression.Call(typeof(Queryable), methodToInvoke, new[] { collectionType, childPropertyType }, collection.Expression, Expression.Quote(orderByExp));
if(comparer != null)
{
// How can I pass the comparator to the OrderBy MethodCallExpression?
// Using the standard LINQ OrderBy, we can do this:
// elements.OrderBy(e => e.Index, new AlphanumComparator())
}
return collection.Provider.CreateQuery<T>(orderByCall);
}
See the comment in the code where I think I should pass the IComparer
... how could I approach this?
I had to approach this differently.
I was trying to create a generic
OrderBy
to be used with MvcContrib Grid, but passing theIComparer
to that customOrderBy
expression did not work as I imagined it would work.So I created this helper that receives a string in dot notation like
Element1.Standard.Chapter.Manual.Name
and then returns anExpression<Func<T, string>>
:This expression typed to T (in this case
Divergence
object type) can then be passed (seefunc.Invoke
) to the standard LINQOrderBy
operator where I can also pass the customIComparer
AlphanumComparator
like this:This involved a little bit more work but solved the problem in a generic fashion the way I wanted it to be.