New to Telerik UI for ASP.NET MVC? Download free 30-day trial

Modifying the DataSourceRequest Object to Map ViewModel Objects to EF Core Entities and Support Filtering and Sorting

Environment

Product Version 2023.1.117
Product DataSource for ASP.NET MVC

Description

I want to use Model Mapping, but my view model object and entities returned by Entity Framework are not identical. Thus, when I follow the Model mapping documentation I get an exception.

I have an EF Core entity:

public class Product
{
 public long ID {get;set;}
 public string Product_Name {get;set;}
}

And a corresponding ViewModel:

public class ProductVM
{
  public long Id {get;set;}
  public string ProductName {get;set;}
}

Solution

A possible approach to resolve the issue is to implement model mapping and map the different model properties to support filtering and sorting. The solution below is suggested by Dave, a member of our forums, and shows how to map model properties so filtering and sorting can be used:

    public static class DataSourceRequestExtensions
    {
        public static void RemapMember(this DataSourceRequest request, string memberName, string newMemberName)
        {
            foreach (var sort in request.Sorts)
            {
                if (sort.Member.Equals(memberName))
                {
                    sort.Member = newMemberName;
                }
            }

            foreach (var filter in request.Filters)
            {
                if (filter is CompositeFilterDescriptor compositeFilterDescriptor)
                {
                    foreach (var compositeFilter in compositeFilterDescriptor.FilterDescriptors)
                    {
                        RemapFilterDescription(compositeFilter, memberName, newMemberName);
                    }
                }
                RemapFilterDescription(filter, memberName, newMemberName);
            }
        }

        private static void RemapFilterDescription(IFilterDescriptor filter, string memberName, string newMemberName)
        {
            if (!(filter is FilterDescriptor descriptor)) return;

            if (descriptor.Member.Equals(memberName))
            {
                descriptor.Member = newMemberName;
            }
        }
    }

Use the extension method to map the model properties so filtering and sorting works as expected:

        public ActionResult Grid_Read([DataSourceRequest] DataSourceRequest request)
        {
            var data = myProductsService.GetAllProducts();
            request.RemapMember("Id", "ID");
            request.RemapMember("ProductName", "Product_Name");
            var dsResult = data.ToDataSourceResult(request, model => new ProductVM()
            {
                Id = model.ID,
                ProductName = model.Product_Name
            });
            return Json(dsResult);
        }

More ASP.NET MVC Grid and DataSource Resources

See Also

In this article