MultiSelect / Server filtering

2 posts, 0 answers
  1. Arthur
    Arthur avatar
    2 posts
    Member since:
    Sep 2017

    Posted 12 Dec 2017 Link to this post

    While running the demo at http://demos.telerik.com/aspnet-core/multiselect/serverfiltering I noticed that the MultiSelect is passing filter query string parameters.

    For example, searching for chef sends the following parameters:

    text: chef
    filter[filters][0][value]: chef
    filter[filters][0][field]: ProductName
    filter[filters][0][operator]: startswith
    filter[filters][0][ignoreCase]: true
    filter[logic]: and

    However the example ignores the filter parameters and implements a contains filter in the controller:

    public JsonResult GetProducts(string text)
    {
        products = products.Where(p => p.ProductName.Contains(text));

     }


    Can the filter parameters be bound to a model? Is there an existing Telerik filter model class that can be used?
  2. Dimitar
    Admin
    Dimitar avatar
    730 posts

    Posted 15 Dec 2017 Link to this post

    Hello Arthur,

    Kendo UI for ASP.NET Core provides extensions that can greatly help you in the described scenario - the DataSoureRequest object and ToDataSourceResult() extension method. With the help of those extensions, we can automatically page, sort, group and filter the request data. This is done in the following way:

    1) Using the DataSourceRequest/DataSourceResult classes from Kendo.MVC assembly requires the use of the aspnetmvc-ajax transport type on the client-side. This is needed as the transport uses specific parameterMap which formats the request parameters for sorting, filtering, etc. in the appropriate way in which the DataSourceRequest ModelBinder will be able to populate the DataSourceRequest instance:
    @(Html.Kendo().MultiSelect()
    ...
    .DataSource(dataSource => dataSource
    .Custom()
    .Type("aspnetmvc-ajax")
    .ServerFiltering(true)
    .Transport(transport => transport
    .Read(read => read.Action("Getproducts", "Home"))
    )
    .Schema(schema => schema
    .Data("Data")
    .Total("Total")
    )
    )
    )

    2) First off we can start by adding DataSourceRequest to the controller action method (read end-point) and decorating it with the .DataSourceRequestAttribute. The DataSourceRequest object will contain request information—page, sort, group, and filter, while the DataSourceRequestAttribute will populate the DataSourceRequest object from the posted data:
    public IActionResult GetProducts([DataSourceRequest] DataSourceRequest request)
    {
    }

    3) Then, inside the read method body, we can retrieve the collection from the database and call the ToDataSourceResult method over the collection to apply paging, sorting, grouping and filter based on the information that is provided by the DataSourceRequest object:
    public IActionResult GetProducts([DataSourceRequest] DataSourceRequest request)
    {
      var products = Enumerable.Range(0, 500).Select(i => new ProductViewModel
      {
        ProductID = i,
        ProductName = "Product " + i
      });
     
      return Json(products.ToDataSourceResult(request));
    }


    With the use of the provided extension methods, the simple implementation above takes care of the server filtering for you automatically without the need to explicitly filter the collection with linQ (as in the provided code snippet). Of course, you can use both approaches to achieve the same result.

    I am also attaching an ASP.NET Core solution, where the above is demonstrated with the MultiSelect widget.

    Regards,
    Dimitar
    Progress Telerik
    Try our brand new, jQuery-free Angular components built from ground-up which deliver the business app essential building blocks - a grid component, data visualization (charts) and form elements.
Back to Top