1

这是我所拥有的: 在此处输入图像描述

单击其中一个框时,下面的列表将在服务器端进行过滤。

如果我选择网格中的行,然后提交过滤器,则会收到以下错误:

“getById 调用了本地缓存中不存在的 ID”

在此处输入图像描述

即使过滤器确实包含我选择的记录,也会出现这种情况。

这是模块:

Ext.define('NG.model.auxClasses.notifications.WhatsNew', {
    extend: 'Ext.data.Model',
    idProperty: 'iD',
    autoLoad: true,
    fields: [
        { name: 'iD', type: 'int' },
        { name: 'isActive', type: 'boolean' },
        { name: 'documentIdentifier', type: 'string' },
        { name: 'sourceSiteName', type: 'string' },
        { name: 'targetSiteName', type: 'string' },
        { name: 'createDate', type: 'date', dateFormat: 'c' },
        { name: 'businessArchiveEvent', type: 'string' },
        { name: 'businessArchive', type: 'string' },
        { name: 'previousWhatsNewEvents' },
        { name: 'isPin', type: 'boolean' },
        { name: 'IsDocumentReadByMe', type: 'boolean' },
        { name: 'isDocumentReadByOthers', type: 'boolean' },
        { name: 'documentYear', type: 'int' },
        { name: 'businessDirection', type:'int'}
    ],

    // self association model
    associations: [{
        type: 'hasMany',
        model: 'auxClasses.notifications.WhatsNew',
        name: 'previousWhatsNewEvents',
        primaryKey: 'id',
        associationKey: 'previousWhatsNewEvents'
    }],

    proxy: {
        type: 'rest',
        url: 'api/WhatsNew/'
    }

});

这里是商店:

Ext.define('NG.store.WhatsNews', {
    extend: 'NG.store.AbstractStore',
    model: 'NG.model.auxClasses.notifications.WhatsNew',
    alias: 'store.whatsnewstore',
    autoLoad:true,
    buffered: true,
    pageSize: 50
});

更新:

我跟着兔子到了洞里,发现了一个我不确定是否可行的解决方法:

这是我失败的地方:

refresh: function() {
        ...

        // Don't need to do this on the first refresh
        if (me.hasFirstRefresh) {
        // Some subclasses do not need to do this. TableView does not need to do this.                   
               if (me.refreshSelmodelOnRefresh !== false) {
                    me.selModel.refresh();
                } else {
                    // However, even if that is not needed, pruning if pruneRemoved is true (the default) still needs doing.
                    me.selModel.pruneIf(); <<< HERE WE FAIL. THIS METHODS CALLS THE GET BY ID
                }
            }

           ...
    }

所以在我看来,我添加了以下视图配置:

viewConfig: {
        refreshSelmodelOnRefresh:true // Workaround : if this is not set to true when the grid will refresh and a record will be selected we will get an ext error 
    },

这已经解决了引发的错误,但我不确定最终结果以及它以后可能会造成什么伤害。

如果有人可以遮光...

有解决方法吗?

4

5 回答 5

1

你可以做几件事-

  1. 将您的 pageSize 增加到至少 100,缓冲存储并不是真正为小型记录集设计的

  2. 使用以下覆盖:

当 store 是缓冲类型时,此覆盖修复了多个错误,并修复了导致初始 hasId 不起作用的错误,因为 store.getById() 方法需要一个 ID 而不是记录,当找不到记录时也会强制双重验证因为它将两个检查放在一个 if 语句中。

@src:http ://www.sencha.com/forum/showthread.php?258397-4.2.0-RC-Selecting-a-grid-s-row-with-a-buffered-store-causes-a-JavaScript -错误/page2

 Ext.override(Ext.selection.Model, {
  storeHasSelected: function(record) {
    var store = this.store,
        records,
        len, id, i, m;

    if (record.hasId()) {
        return store.getById(record.getId());
    } else {
        if (store.buffered) {//on buffered stores the map holds the data items
            records = [];
            for (m in store.data.map) {
                records = records.concat(store.data.map[m].value);
            }
        } else {
            records = store.data.items;
        }
        len = records.length;
        id = record.internalId;


        for (i = 0; i < len; ++i) {
            if (id === records[i].internalId) {
                return true;
            }
        }
    }
    return false;
  }
});

如果 1 和 2 都不起作用,请尝试:

Ext.view.AbstractView.override({
    refresh: function() {
        var me = this,
            targetEl,
            targetParent,
            oldDisplay,
            nextSibling,
            dom,
            records;

        if (!me.rendered || me.isDestroyed) {
            return;
        }

        if (!me.hasListeners.beforerefresh || me.fireEvent('beforerefresh', me) !== false) {
            targetEl = me.getTargetEl();
            records = me.getViewRange();
            dom = targetEl.dom;

            // Updating is much quicker if done when the targetEl is detached from the document, and not displayed.
            // But this resets the scroll position, so when preserving scroll position, this cannot be done.
            if (!me.preserveScrollOnRefresh) {
                targetParent = dom.parentNode;
                oldDisplay = dom.style.display;
                dom.style.display = 'none';
                nextSibling = dom.nextSibling;
                targetParent.removeChild(dom);
            }

            if (me.refreshCounter) {
                me.clearViewEl();
            } else {
                me.fixedNodes = targetEl.dom.childNodes.length;
                me.refreshCounter = 1;
            }

            // Always attempt to create the required markup after the fixedNodes.
            // Usually, for an empty record set, this would be blank, but when the Template
            // Creates markup outside of the record loop, this must still be honoured even if there are no
            // records.
            me.tpl.append(targetEl, me.collectData(records, me.all.startIndex));

            // The emptyText is now appended to the View's element
            // after any fixedNodes.


            if (typeof records !== 'undefined' && records !== undefined && records && records.length < 1) { 
                // Process empty text unless the store is being cleared.
                if (!this.store.loading && (!me.deferEmptyText || me.hasFirstRefresh)) {
                    Ext.core.DomHelper.insertHtml('beforeEnd', targetEl.dom, me.emptyText);
                }
                me.all.clear();
            } else {
                me.collectNodes(targetEl.dom);
                me.updateIndexes(0);
            }

            // Don't need to do this on the first refresh
            if (me.hasFirstRefresh) {
                // Some subclasses do not need to do this. TableView does not need to do this.
                if (me.refreshSelmodelOnRefresh !== false) {
                    me.selModel.refresh();
                } else {
                    // However, even if that is not needed, pruning if pruneRemoved is true (the default) still needs doing.
                    me.selModel.pruneIf();
                }
            }

            me.hasFirstRefresh = true;

            if (!me.preserveScrollOnRefresh) {
                targetParent.insertBefore(dom, nextSibling);
                dom.style.display = oldDisplay;
            }

            // Ensure layout system knows about new content size
            this.refreshSize();

            me.fireEvent('refresh', me);

            // Upon first refresh, fire the viewready event.
            // Reconfiguring the grid "renews" this event.
            if (!me.viewReady) {
                // Fire an event when deferred content becomes available.
                // This supports grid Panel's deferRowRender capability
                me.viewReady = true;
                me.fireEvent('viewready', me);
            }
        }
    }
});
于 2013-11-13T13:08:47.303 回答
1

在我的代码中,我使用了带有网格的缓冲存储,然后我得到了这个错误。

我用这个解决了

selModel: {
    pruneRemoved: false
}
于 2015-07-08T06:37:56.520 回答
0

请尝试此覆盖

    Ext.data.Store.override({
        getById: function(id) {
            var result = (this.snapshot || this.data).findBy(function(record) {
                return record.getId() === id;
            });
            if (this.buffered && !result) {
                return [];
            }
            return result;
        }
    });
于 2014-05-24T20:59:30.887 回答
0

对于 ExtJS 5 覆盖 BufferedStore 而不是 Store:

Ext.data.BufferedStore.override({
    getById: function(id) {
        var result = (this.snapshot || this.data).findBy(function(record) {
            return record.getId() === id;
        });
        if (this.buffered && !result) {
            return [];
        }
        return result;
    }
});
于 2015-02-26T10:45:33.197 回答
0

您不需要使用任何上述覆盖。如果您在使用缓冲存储时遇到此错误,只需按照此处指定的方式设置 pruneRemoved: false 属性:http://docs.sencha.com/extjs/4.2.3/#! /api/Ext.selection.Model-cfg -prune 已移除

例如

selModel: Ext.create('Ext.selection.RowModel', {
                pruneRemoved: false
})
于 2015-06-10T03:40:55.830 回答