Kendo网格服务器端分组 [英] Kendo grid server side grouping

查看:69
本文介绍了Kendo网格服务器端分组的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我将Asp net 5,NHibernate 3.3和Kendo UI MVC包装器用于网格以呈现客户订单表.数据库中已经有很多订单,并且数量一直在增长.因此,我决定使用服务器端分页以避免从数据库中获取所有订单.据我所知,您无法手动进行分页,也无法将筛选,排序和分组委托给ToDataSourceResult方法.要么全部要么一无所有.因此,我尝试实现所谓的自定义绑定" .没问题,直到我开始分组.我需要先进行分组,然后在组内进行排序,然后提取特定页面的数据以及所有这些数据,而无需将所有数据加载到内存中.我的代码是这样的(为了简化阅读,我将其全部整合在一起):

I am using Asp net 5, NHibernate 3.3 and Kendo UI MVC wrapper for grid to render the table of client orders. There are lots of orders in database already and the number is constantly growing. So I decided to use server side paging to avoid fetching all orders from database. As far as I know you can't do paging manually and delegate filtering, sorting and grouping to ToDataSourceResult method. It's either all or nothing. Therefore I made an attempt to implement so called 'custom binding'. No problem until I get to grouping. I need to group first, then sort inside of a group, then extract data for specific page and all that without loading all data to memory. My code is something like this (I put it all in one piece to simplify reading):

var orderList = CurrentSession.QueryOver<Order>();

// Filtering. Filter is a search string obtained from DataSourceRequest
var disjunction = new Disjunction();
disjunction.Add(Restrictions.On<Order>(e => e.Number).IsLike("%" + filter + "%"));
disjunction.Add(Restrictions.On<Order>(e => e.Customer).IsLike("%" + filter + "%"));
orderList = orderList.Where(disjunction);

// Sorting. sortColumn is also from DataSourceRequest
switch (sortColumn)
{
        case "Number":
            orderList = orderList.OrderBy(x => x.Number).Desc;
            break;
        case "GeneralInfo.LastChangeDate":
            orderList = orderList.OrderBy(x => x.LastChangeDate).Desc;
            break;
        default:
            orderList = orderList.OrderBy(x => x.Number).Desc;
            break;
     }
}

// Total is required for kendo grid when you do paging manually
var total = orderList.RowCount();


var orders = orderList
    .Fetch(x => x.OrderGoods).Eager
    .Fetch(x => x.OrderComments).Eager
    .Fetch(x => x.Documents).Eager
    .Fetch(x => x.Partner).Eager
    .Skip((request.Page - 1)*request.PageSize).Take(request.PageSize).List();

我将很高兴就如何在此处添加分组提供任何建议.

I will be glad to have any advice on how to add grouping here.

推荐答案

我花了几个月的时间来弄清楚使用Kendo数据源和Kendo Grid进行服务器端分组的情况.分页,排序和过滤非常简单.但是无论出于何种原因,Telerik都没有为诸如分组之类的关键LOB流程提供足够的支持文档.很高兴您发布此问题,以便有机会分享我的代码.

I worked for literally months to figure out server-side grouping using the Kendo DataSource with a Kendo Grid. Paging, sorting and filtering were fairly easy. But for whatever reason, Telerik did not offer sufficient support documentation for such a critical LOB process as grouping. I’m glad you posted this question so I’d have an opportunity to share my code.

解决方案

基本上,解决方案归结为两个关键部分,可以在以下示例项目中进行查看: https: //www.dropbox.com/s/ygtk8rwl1hwjvth/KendoServerGrouping.zip?dl=0

Basically, the solution comes down to knowing 2 key parts, and they can be viewed in the following sample project: https://www.dropbox.com/s/ygtk8rwl1hwjvth/KendoServerGrouping.zip?dl=0

您要下载的Visual Studio(2012 | 2013)解决方案中只有一个Web应用程序项目,其中包含对Kendo.Mvc库的引用.您可以从Telerik的控制面板安装程序中下载最新的 ASP.NET UI 二进制文件.安装后,这些二进制文件将位于以下Windows目录中: C:\ Program Files(x86)\ Telerik \ UI for ASP.NET MVC [Telerik发行版] \ wrappers \ aspnetmvc \ Binaries \ [您的MVC版本] \ Kendo.Mvc.dll .

There is a single web application project in the Visual Studio (2012 | 2013) solution you’re downloading, which contains a reference to the Kendo.Mvc library. You can download the latest UI for ASP.NET binaries from Telerik's Control Panel installation program. The binaries will be located in the following Windows directory after install: C:\Program Files (x86)\Telerik\UI for ASP.NET MVC [Telerik Release Version]\wrappers\aspnetmvc\Binaries\ [Your Version of MVC]\Kendo.Mvc.dll.

注意:我的解决方案使用Telerik的MVC传输机制,该机制可提供完整的服务器端分页,过滤,排序以及最显着的分组功能. 但是,我使用纯JavaScript来配置Kendo数据源,而不是MVC包装器.不过,我最近在Telerik的文档中找到了一个链接,该链接显示了Razor/ASPX中的MVC包装器声明.

Note: My solution uses Telerik’s MVC transport mechanism, which provides full-fledged server-side paging, filtering, sorting and, most notably, grouping. However, I use pure JavaScript to configure the Kendo DataSource and not the MVC wrappers. Still, I've recently found a link in Telerik's documentation that shows the MVC wrapper declaration in Razor/ASPX.

服务器魔术师

基本上, 魔术 的第一部分是以下服务器端代码,它们位于 KendoServerGrouping.Web \ Controllers 控制器中的示例WebApi控制器中. strong>目录:

Basically, the first part of the magic is the following server side code, residing in the sample WebApi controller in the KendoServerGrouping.Web\Controllers directory:

    [System.Web.Http.AcceptVerbs("GET", "ASPNETMVC-AJAX")]
    public Kendo.Mvc.UI.DataSourceResult GetAllAccounts([System.Web.Http.ModelBinding.ModelBinder(typeof(WebApiDataSourceRequestModelBinder))] Kendo.Mvc.UI.DataSourceRequest request)
    {
        var kendoRequest = new Kendo.Mvc.UI.DataSourceRequest
        {
            Page = request.Page,
            PageSize = request.PageSize,
            Filters = request.Filters,
            Sorts = request.Sorts,
            Groups = request.Groups,
            Aggregates = request.Aggregates
        };

        // Set this to your ORM or other data source
        IQueryable accounts = dbContext.Accounts;

        /*
           The data source can even be a MongoDB collection using the
           .AsQueryable() extension and the MongoDB C# driver

           var accounts = collection.FindAllAs<Account>().AsQueryable();
        */

        var data = accounts.ToDataSourceResult(kendoRequest);

        var result = new DataSourceResult()
        {
            AggregateResults = data.AggregateResults,
            Data = data.Data,
            Errors = data.Errors,
            Total = data.Total
        };

        return result;
    }

这是网格在用户与其进行交互时将自动神奇地处理的四个服务器端操作中所有您需要的.请特别注意方法上方的AcceptVerbs属性;它必须包含"ASPNETMVC-AJAX" 属性,DataSourceRequest输入参数才能正常工作. ToDataSourceResult()是Kendo.Mvc.dll库的最新版本提供的扩展名,

This is all you’ll need for any of the four server-side actions that the grid will handle auto-magically when the user interacts with it. Pay special attention to the AcceptVerbs attribute above the method; it must include the "ASPNETMVC-AJAX" attribute for the DataSourceRequest input parameter to work properly. ToDataSourceResult() is an extension provided by recent versions of the Kendo.Mvc.dll library, which I pointed to earlier.

(据我所知)上面的代码将与任何IQueryable数据源一起使用,例如来自ORM的数据源(我已经测试了Entity Framework和Telerik数据访问/开放访问).我还能够使用MongoDB C#驱动程序对MongoDB集合进行分组.但是,这仅是概念验证,尚未经过性能测试.

The code above will (to my knowledge) work with any IQueryable data source, such as those from ORMs (I've tested Entity Framework and Telerik Data Access/Open Access). I've also been able to group a MongoDB collection using the MongoDB C# driver. However, this is meant as a proof-of-concept, and it has not been tested for performance.

就本示例而言,WebAPI控制器中有静态数据源来伪造IQueryable集合.自然地,当您交换了自己的数据源后,您可以从第45-57行中删除静态数据.

For the purposes of this example, there is static data source in the WebAPI controller to fake an IQueryable collection. Naturally, you can delete the static data from lines 45-57 when you've swapped in your own data source.

客户魔力

Kendo DataSource自动从网格中传递一个专门的DataSourceRequest对象,该对象包含用于服务器端分页,过滤,排序和分组的所有参数, 提供 以下JavaScript中的DataSource模式:

The Kendo DataSource automatically passes in a specialized DataSourceRequest object from the grid containing all the parameters for server-side paging, filtering, sorting and grouping, provided you wrap your DataSource schema inside the following JavaScript:

schema: $.extend(true, {}, kendo.data.schemas["aspnetmvc-ajax"], {
});

这也许是我所追踪的最难捉摸的代码行.在几个月的时间里,与Telerik进行了大约十二次交流,以使他们咳嗽起来.即使在那时,它也完全是偶然地被揭示出来的.为什么在他们的文档中没有这么关键的细微差别,这超出了我的理解.

This was perhaps the single most elusive line of code I’ve ever tracked down. It took about a dozen exchanges with Telerik over several months to get them to cough it up. And even then, it was by pure chance that it was revealed. Why such a critical nuance was absent in their documentation is beyond me.

仔细检查index.html文件下半部分的每个Kendo DataSource配置设置.最重要的是,请注意其中没有的内容,例如batchmvcTransport选项.包括后一个选项将以某种方式否定上述"aspnetmvc-ajax" 架构属性.

Carefully review each of the Kendo DataSource configuration settings toward the bottom half of index.html file. Most importantly, pay attention to what isn’t there, such as the batch and mvcTransport options. Including the latter option somehow negates the above "aspnetmvc-ajax" schema attribute.

在数据源的 parmaterMap 函数中,请注意,当(且仅当)执行读取操作时,必须存在以下行:

In the DataSource's parmaterMap function, make note that when – and only when - performing a read operation, the following line must be present:

return mvcTransport.parameterMap(options, operation);

在执行数据源之前,您还希望确保将其包含在HTML中:

You will also want to be sure to include this in your HTML, before the DataSource executes:

<script src="//cdn.kendostatic.com/[Version]/js/kendo.aspnetmvc.min.js"></script>

最终结果

运行 KendoServerGrouping.Web 项目( index.html ),如果一切顺利,将用5个包含 AccountId 的记录填充网格. strong>,帐户名称 AccountTypeCode CreatedOn 字段.如果将可见网格行数设置为 2 并按 AccountTypeCode CreatedOn 分组,则会看到该分组遍历了分页,我相信这是您想要的最终结果.

Run the KendoServerGrouping.Web project (index.html) and, if all goes well, a grid will be populated with 5 records containing AccountId, AccountName, AccountTypeCode and CreatedOn fields. If you set the number of visible grid rows to 2 and group by AccountTypeCode or CreatedOn, you’ll see that the grouping traverses the paging, which I believe is the end result you are looking for.

我希望示例项目能够正常运行,并且适合您的情况.如有任何问题,请告诉我,我们将尽力为您提供帮助.

I hope the sample project works and is a good fit for your situation. Please let me know if you have any questions, and I’ll do my best to help.

P.S.这是我的第一篇SO文章,因此,如果某些内容不符合SO标准,请对我轻松一点.祝你好运!

P.S. This is my first post to SO, so please go easy on me if something isn’t up to SO standards. Good luck!

这篇关于Kendo网格服务器端分组的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆