Javascript 对dgrid 0.3.6排序时重复的行

Javascript 对dgrid 0.3.6排序时重复的行,javascript,dojo,dgrid,Javascript,Dojo,Dgrid,我一直在使用dgrid 0.3.2和JsonRest来显示数据表。最近,我一直在考虑升级到dgrid 0.3.6或0.3.7。工作原理基本相同,但在较新版本的dgrid中,如果用户单击列标题进行足够快的排序,网格将开始显示重复的行。我已经验证了响应JSON和范围是正确的,当我们使用dgrid 0.3.2时,这似乎没有发生 下面是一个简单的测试用例,它再现了这个问题,并模拟了我们如何设置网格和存储。我做错什么了吗?如果我不将JsonRest封装在缓存中,我就不会遇到这个问题,因此我确信问题存在,但

我一直在使用dgrid 0.3.2和JsonRest来显示数据表。最近,我一直在考虑升级到dgrid 0.3.6或0.3.7。工作原理基本相同,但在较新版本的dgrid中,如果用户单击列标题进行足够快的排序,网格将开始显示重复的行。我已经验证了响应JSON和范围是正确的,当我们使用dgrid 0.3.2时,这似乎没有发生

下面是一个简单的测试用例,它再现了这个问题,并模拟了我们如何设置网格和存储。我做错什么了吗?如果我不将JsonRest封装在缓存中,我就不会遇到这个问题,因此我确信问题存在,但我不确定不缓存JSON响应的性能后果

<!doctype html>
<html>

<head>
<%
    String dgridVer = request.getParameter("dgridVer");
    if (dgridVer==null) { dgridVer = "0.3.6"; }
%>
<script type="text/javascript">
    var dojoConfig = {
        isDebug: true,
        baseUrl: 'dojo',
        packages: [
            { name: 'dojo',      location: 'dojo' },
            { name: 'dijit',     location: 'dijit' },
            { name: 'dojox',     location: 'dojox' },
            { name: 'dgrid',     location: 'dgrid-<%=dgridVer%>' },
            { name: 'put-selector',     location: 'put-selector' },
            { name: 'xstyle',    location: 'xstyle' },
            { name: 'datagrid', location: '../datagrid' }
        ]
    };
</script>
<script src="dojo/dojo/dojo.js"></script>
</head>

<body>
Try sorting a column as fast as you can.  Look for duplicated rows.<br>
Using dgrid version: <%=dgridVer %><p>

<div id='gridDiv'></div>

<script>
require(['dgrid/Grid', 'dgrid/extensions/Pagination', 'dojo/store/JsonRest',
            'dojo/store/Cache', 'dojo/store/Memory', 'dojo/_base/declare', 'dojo/domReady!'], 
    function(Grid, Pagination, JsonRest,
                Cache, Memory, declare) {

    var columns = [
        { field: "first", label: "First Name" },
        { field: "last",  label: "Last Name" },
        { field: "age",    label: "Age" }
    ];

    var store = new JsonRest({
        target: 'testData.jsp',
        sortParam: "sortBy"
    });
    store = Cache(store, Memory());

    var grid = new (declare([Grid, Pagination]))({
        columns: columns,
        store: store,
        loadingMessage: 'Loading...',
        rowsPerPage: 4,
        firstLastArrows: true
    }, 'gridDiv');

});
</script>

</body>

</html>

var dojoConfig={
是的,
baseUrl:'dojo',
套餐:[
{名称:'dojo',位置:'dojo'},
{name:'dijit',location:'dijit'},
{名称:'dojox',位置:'dojox'},
{名称:'dgrid',位置:'dgrid-'},
{name:'put selector',location:'put selector'},
{name:'xstyle',location:'xstyle'},
{name:'datagrid',位置:'../datagrid'}
]
};
尽可能快地对列进行排序。查找重复的行。
使用dgrid版本: 需要(['dgrid/Grid'、'dgrid/extensions/Pagination'、'dojo/store/JsonRest', “dojo/store/Cache”、“dojo/store/Memory”、“dojo/_base/declare”、“dojo/domReady!”, 函数(网格、分页、JsonRest、, 缓存、内存、声明){ 变量列=[ {字段:“first”,标签:“first Name”}, {字段:“last”,标签:“last Name”}, {字段:“年龄”,标签:“年龄”} ]; var store=newjsonrest({ 目标:“testData.jsp”, sortParam:“sortBy” }); store=缓存(store,Memory()); var grid=new(声明([grid,分页])({ 列:列, 店:店,, loadingMessage:“正在加载…”, 行页码:4, 第一个箭头:对 }"gridDiv",; });
检查的默认实现,尤其是
查询
查询引擎
函数。默认情况下,它们总是首先到达主存储,在您的情况下,主存储就是
JsonRest
存储。只有在加载数据后,缓存存储才会更新(在您的情况下是
内存
存储)

现在,如果您在DGrid文件中选中函数
\u setSort
,并在DGrid中选中函数
refresh
,您将看到默认情况下,DGrid调用当前
存储
查询
方法,以获得不同排序的项目的新列表。在您的例子中,存储是dojo/store/Cache

总之,当用户单击列进行排序时,DGrid查询
缓存
,后者依次查询
JsonRest
,后者依次查询服务器,然后服务器返回新数据,
缓存
将其存储在
内存
存储中

您可以通过Firebug(Firefox扩展)来确认这一点。在我的例子中,每当我尝试排序时,Firebug都会向服务器显示一个新请求以获取新数据

当有很多行时,这是有意义的,因为DGrid设计为仅加载第一批行,然后在用户向下滚动时更新网格。当排序发生更改时,第一批可见的行可能不同,并且可能尚未加载,因此DGrid必须首先加载它们

但在我的例子中,Json请求在单个请求期间返回所有数据。我不喜欢默认实现,并实现了自己的缓存存储,在更改排序时不需要访问服务器。我现在不能分享这个实现,但是当我有时间整理代码时,我会尝试这样做

就目前而言,如果只切换到
JsonRest
store,您不应该注意到任何性能问题(考虑到在更改排序时,无论如何都有到服务器的行程)


我不确定是什么导致了重复行的具体问题,但我记得在缓存存储未正确实现时也看到了这一问题(如果我回忆正确,它与加载数据时的延迟请求有关)。您可以尝试通过在
Cache
存储的
get
query
函数中添加断点(同样使用Firebug)来调试它。我敢打赌,当用户更改排序后,
query
请求仍在从服务器加载数据时,DGrid会尝试使用
get
方法加载特定行(该方法会命中缓存)。但是我可能错了,所以如果可以的话,请先确认一下。

很抱歉,我花了这么长时间才回复。谢谢你的回复,你的想法和我的一样。我无法找出dgrid代码中发生了什么变化,但在该行为发生变化时,我将其隔离到了0.3.5。我创建并提到了我提出的一个解决方案——在当前正在运行排序时,只需禁用列排序。