Reputation: 826
I am retriveing some data using Entity Framework like so:
var items = GetItems(storeNumber);
Sort(items);
Page(items);
return await items.ToListAsync();
I have these private helper methods:
private IQueryable<Item> GetItems(string storeNumber)
{
return _dbContext.Items.Where(x => x.StoreNumber == storeNumber);
}
I sort the results using Dynamic LINQ.
private void Sort(IQueryable<Item> items, string fieldToSort, string sortDirection)
{
items = items.OrderBy($"{fieldToSort} {sortDirection}");
}
In my Page method I get the exception
The method 'OrderBy' must be called before the method 'Skip'
private void Page(IQueryable<Item> items, int skip, int take)
{
items = items.Skip(skip).Take(take);
}
I had suspected that the reason for the error was because items needs to be IOrderedQueryable<Item>
but there is no overload for the Dynamic LINQ OrderBy which returns IOrderedQueryable<T>
.
If I extract the Sort and Page code into the same method, using var
it's no longer an issue, it infers the type. The problem seems to be using the IQueryable
interface when sorting and paging. Is there a way I can break up this logic into separate methods but still use Dynamic LINQ for sorting?
Any help is much appreciated.
Upvotes: 1
Views: 1178
Reputation: 4350
You should return the newly constructed IQueryable
from the Sort() and the Page() methods, just as you do for GetItems().
If you "rewrite" a parameter value inside a method like this, it has no effect on the value originally passed in to the parameter, because C# uses by-value parameter passing semantics
See this for more reference: https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/passing-parameters
Upvotes: 2