This is a migrated thread and some comments may be shown as answers.

FilterDescriptor.cs (IFilterDescriptor) can we see what it looks like?

21 Answers 1320 Views
General Discussions
This is a migrated thread and some comments may be shown as answers.
This question is locked. New answers and comments are not allowed.
Vesselin Obreshkov
Top achievements
Rank 2
Vesselin Obreshkov asked on 26 Jun 2012, 04:40 PM
Trying to make our sorting and filtering working with what comes in a DataSourceRequest but since the source codes for Kendo.Mvc.dll aren't available (yet?), can we see what your FilterDescriptor looks like (I can only see an IFilterDescriptor interface which has one method by going to object definitions).

I can submit a support ticket if that's a preferred way.

Thanks

21 Answers, 1 is accepted

Sort by
0
Atanas Korchev
Telerik team
answered on 27 Jun 2012, 07:03 AM
Hello Vesselin,

 The FilterDescriptor is a public class which is available in the Kendo.Mvc namespace. It is basically the same as in Telerik Extensions for ASP.NET MVC. I have attached this file for your convenience.

 On a side note the source code will be available with the official release.

All the best,
Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 27 Jun 2012, 09:15 PM
Very nice, thank you!

We had a similair question before - may I suggest that you expose the internal sorting and filtering function as public? That is - to use it the filtering and sortering right now we concluder (correctly?) that you have to call ToDataSourceResult() and use the result. It would however be nice if the sort/filter/etc functionality is exposed as well.

Otherwise, very clean solution (returing Json(....ToDataSourceRequest()) etc) compared to the [GridAttribute] solution in Telrik ASP MVC. Very nice and transparent!

Thanks!
/Victor
0
Atanas Korchev
Telerik team
answered on 28 Jun 2012, 07:45 AM
Hello Victor,

 Those are already exposed as IQyeryable extension methods: Page, Sort, GroupBy etc.

All the best,
Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 28 Jun 2012, 09:18 AM
Hi and thanks for your reply!

We know that those functions are exposed, however it would be nice if the function calling all the separate functions (sort, filter, etc) was exposed as well. Preferably taking in IQueryable<T> and returning IQuearyable<T> if possible.

Edit: Since we feel we might miss something if we use the individual functions we right now use the ToDataSourceResult() with some casting to get it back to the original type. We do this in the server side function generating the grid to get the same behaviour as for the functions returning the Json results for paging/sorting/etc.


/Victor
0
Atanas Korchev
Telerik team
answered on 28 Jun 2012, 10:42 AM
Hi Victor,

 We don't have such a function because we need the Total count of records as well. It would be lost if we process all data in a single method.

All the best,
Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 28 Jun 2012, 01:51 PM
Hi,
We realize that, and we realize that it would not (and should not) replace the ToDataSourceResult() function, it would still be convenient to have the sort/filter/etc functionality exposed in a single function. We could then do something like:

var viewModel = new CustomViewModel();
var unfilteredList = GetCustomViewModelList();
viewModel.TotalRows = unfilteredList.Count();
viewModel.Records = unfiltereredList.ApplyRequestFiltering(request);
return View(viewModel);

and refactor most of this code to be common between server side and ajax request functions. One reason we want this is since we often have som post-processing that shoud be done after sorting and filtering has been done to add some custom, complex properties in memory, similair to:

var viewModel = new CustomViewModel();
var unfilteredList = GetCustomViewModelList();
viewModel.TotalRows = unfilteredList.Count();
viewModel.Records = unfiltereredList.ApplyRequestFiltering(request).ToList(); //actual EF query to result in memory
viewModel.Records.ForEach(record => record.CustomProperty = String.Join(",", record.CustomListProperty));
return View(viewModel);

Right now this is possible via Cast<CustomViewModel> after calling ToDataSourceResult(), unfortunately this creates quite cumbersome code. So optimally we would like the option to do something like:

//Code as before but refactored
return View(alreadyFilteredAndSortedViewModel.AddCustomCalculatedProperties().ToDataSourceResult(totalCount));

Hope this clarifies our objectives. Of course the implementation could be different, but the goal would for us be:
  • Possibility to refactor out creation, filtering and sorting to a method to be used for both server-side and ajax requests
  • Possibility to use non-db functions on the resulting, filtered, request (such as String.Join()), thus applied on 20 results rather than on 20000.
/Victor
0
Atanas Korchev
Telerik team
answered on 28 Jun 2012, 03:21 PM
Hello Victor,

 I will add this for to our TODO list. Hopefully it would make it in the final release.

Greetings,
Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 28 Jun 2012, 03:23 PM
Perfect, thanks a lot.

/Victor
0
Atanas Korchev
Telerik team
answered on 02 Jul 2012, 11:23 AM
Hello Victor,

 While researching the implementation of such extension methods I found to obstacles. The ToDataSourceResult extension method supports aggregates and grouping. However the result from those two operations is no longer IQueryable<T>. This means that an extension method which takes IQueryable<T> and returns IQueryable<T> will not support aggregates and grouping. In this case I don't think such a method would have any value.

 Right now we can either expose a method called ProcessDataSourceRequest which will not support (and never support) grouping and aggregates or just skip that method altogether. What do you think?

Regards,
Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 02 Jul 2012, 01:46 PM
Hi again and thanks for getting back to me.

A more complete example of what we are trying to accomplish can be found in this other thred: http://www.kendoui.com/forums/mvc/grid/grid-reorders-server-side-data-even-when-no-sort-order-is-specified.aspx#2170196

Basically the part feels very cumbersome, but that was the best we could come up with for now:
var result = producers
                .Take(request.PageSize)
                .ToList()
                .ToDataSourceResult(request);
var producersList = result.Data.Cast<ProducerViewModel>().ToList();

Hopefully this clarifies some, otherwise, please get back to us!

/Victor
0
Atanas Korchev
Telerik team
answered on 02 Jul 2012, 02:42 PM
Hi Victor,

Your code will also fail if grouping or aggregates are enabled. The following cast will fail: 

result.Data.Cast<
ProducerViewModel>().ToList(); 

So the question I am asking is how grouping and aggregates should be handled in this case - an exception should be thrown or what?

Regards,
Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 02 Jul 2012, 02:57 PM
Oh, I see... We actually only tried sorting and filtering, so we didnt realize grouping would not work.

Anyway, as you can see from the linked thread (previous post), we want to be able to post-process the correct page of results in-memory.

So - I suppose what we need to do is (have I missed any steps?):
  1. Sort
  2. Skip
  3. Take
  4. ToList (DB => Memory)
  5. Custom post processing (processing that cannot be done on the DB side)
  6. ToDataSourceResult

Also in (6) we would need to provide some inputs from (1)-(3), such as total count and current page number.

/Victor

0
Atanas Korchev
Telerik team
answered on 02 Jul 2012, 04:05 PM
Hi Victor,

 This seems about right. You can reset the paging and sorting info to avoid double paging and sorting:

request.Page = 0;
request.PageSize = 0;

result = data.Skip().Take().OrderBy().ToList().ToDataSourceResult(request);

Regards,

Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 03 Jul 2012, 07:23 AM
Hi,
Thanks for that! However I am not sure how to do this correctly currently. 1-5 is not Kendo related and will be done "as usual" (with changes to work with datasourcerequest of course), however 6 I am not sure about...

How do I return a datasource-result correctly? That is - before (1) i take out the full IQueryable the count, I do 1-5. I then have a list of say 25 sorted items (from page 10, out of 1000) and want to return the correct datasourceresponse supporting aggregates and filters.

/Victor


0
Atanas Korchev
Telerik team
answered on 03 Jul 2012, 07:46 AM
Hello Victor,

 I am starting to think that this problem should be solved in a different manner. If the only thing you want is to do some sort of projection over the process data we can probably think find another solution. How about something like this?

var result = data.ToDataSourceResult(request, (db) => toMemory(db)) 

The extension method would take the selector and use it internally to do the required projections. Do you think this would work?

Regards,

Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 03 Jul 2012, 08:03 AM
Hmm...

Sounds like a very tempting solution! I am not sure exactly how you think about implementing it, but for us we need to be able to provide a custom projection. Usually we use Automapper  for our projections and will need for custom aggregate functions not supported in the DB, such as String.Join() in the simplest case. Automapper is of course not a requirement, but the syntax is very appealing:
IEnumerable<OrderViewModel> dto = Mapper.Map<IEnumerable<Order>, IEnumerable<OrderDto>>(ordersFromDb);

If I understand you correctly we would do something like one of these two:
(1)
var db = companiesSet.Where(...);
var result = data.ToDataSourceResult(request, (db) => toMemory(db));
 
...
function CompanyViewModel toMemory(Company dbCompany) {
return  Mapper.Map<Company, CompanyViewModel>(dbCompany);
   //Or non Automapper projection
}


(2)
var db = companiesSet.Where(...).Select(c => new CompanyViewModel(...));
var result = data.ToDataSourceResult(request, (db) => inMemoryPostProcessing(db));
 
...
function CompanyViewModel inMemoryPostProcessing(CompanyViewModel companyViewModel) {
    //Custom in memory code such as sting join
}


Is that what you suggest?
/Victor
0
Atanas Korchev
Telerik team
answered on 03 Jul 2012, 08:26 AM
Hello Victor,

 Yes, #1 is the way I was thinking it could work. The implementation won't be easy but is still doable and would work in all cases (even when grouping and aggregates are involved).

Regards,
Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 03 Jul 2012, 08:49 AM
#1 seems like a very good solution, and as you say a general one that will work well.

/Victor
0
Atanas Korchev
Telerik team
answered on 03 Jul 2012, 11:16 AM
Hi Victor,

 I've just implemented that overload. The feature would be available in the official release.

All the best,
Atanas Korchev
the Telerik team
Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
0
Victor
Top achievements
Rank 1
answered on 03 Jul 2012, 11:21 AM
Fantastic! That will be very helpful for more advanced mappings!

/Victor
0
Mo
Top achievements
Rank 1
answered on 20 Jul 2012, 07:37 PM
Is this feature is the newest release- 2012.2.710? I have tried to use it in a very similar manner to what was requested, using AutoMapper, and get an exception:

My code:

DataSourceResult result = this.StateProvinceService
                .GetQueryable()
                .ToDataSourceResult<StateProvince, StateProvinceModel>(
                    request,
                    province => Mapper.Map<StateProvince, StateProvinceModel>(province));

The result:

LINQ to Entities does not recognize the method 'XYZ.Web.Areas.Admin.Models.StateProvinceModel Map[StateProvince,StateProvinceModel](XYZ.Model.StateProvince)' method, and this method cannot be translated into a store expression.


Any advice?
Tags
General Discussions
Asked by
Vesselin Obreshkov
Top achievements
Rank 2
Answers by
Atanas Korchev
Telerik team
Victor
Top achievements
Rank 1
Mo
Top achievements
Rank 1
Share this question
or