【问题标题】:Clear data from Ember's Store before doing findAll在执行 findAll 之前从 Ember 的商店中清除数据
【发布时间】:2025-12-31 08:45:10
【问题描述】:

使用 Ember 1.11 我有一个可以运行参数化 find() 的搜索功能,但是我希望能够返回到查找之前的状态,只有之前存在的记录。在我的应用中,这是 API 返回的不带查询参数的记录。

我的路线的模型挂钩

  model: function(params) {
    if (params.q) {
      return this.store.find('project', params);
    } else {
      return this.store.findAll('project');
    }
  }

但是,当前发生的是用户返回时(通过使用清除查询参数的操作):

backToMyProjects: function() {
  this.set('q', null);
}

this jsbin 是来自@lolmaus 的一个例子,它帮助我完成了这个工作) 那么所有的记录仍然在存储中,所以当它执行 findAll() 时,它会取回两组记录,而我真正想要的是它清除存储,然后使用 findAll() 中的记录。服务器 API 调用在两个地方都正确发生,只是模型钩子在没有参数的情况下被调用它被使用参数调用一次之后,然后存储中有额外的记录。

然后我尝试添加this.store.unloadAll('project'),但在从参数化查询返回到不带参数的查询后出现错误。

更新模型挂钩

model: function(params) {
  if (params.q) {
    return this.store.find('project', params);
  } else {
    this.store.unloadAll('project');
    return this.store.findAll('project');
  }
},
//this isn't new, just forgot to put it earlier. when the query param is modified, the model hook is called again (as I understand it).
queryParams: {
  q: {
    refreshModel: true
  } 
}

错误信息

Error while processing route: projects Assertion Failed: calling set on destroyed object Error: Assertion Failed: calling set on destroyed object
    at new Error (native)
    at Error.EmberError (http://localhost:4200/assets/vendor.js:22615:21)
    at Object.Ember.default.assert (http://localhost:4200/assets/vendor.js:15716:13)
    at Object.set (http://localhost:4200/assets/vendor.js:26367:22)
    at exports.default.mixin.Mixin.create.set (http://localhost:4200/assets/vendor.js:41034:20)
    at Ember.Object.extend.flushCanonical (http://localhost:4200/assets/vendor.js:69680:14)
    at ember$data$lib$system$relationships$state$has_many$$ManyRelationship.flushCanonical (http://localhost:4200/assets/vendor.js:71436:22)
    at Queue.invoke (http://localhost:4200/assets/vendor.js:11425:18)
    at Object.Queue.flush (http://localhost:4200/assets/vendor.js:11490:13)
    at Object.DeferredActionQueues.flush (http://localhost:4200/assets/vendor.js:11295:19)

【问题讨论】:

  • this.store.unloadAll 是正确的。请发布准确的错误消息和您尝试过的代码。
  • 我在我的一个应用程序中尝试了model() { this.store.unloadAll('book'); return this.store.findAll('book'); },但没有收到任何运行时错误。正如 Gaurav 所说,请发布确切的错误消息
  • 添加了错误信息。这不会在页面的初始加载(路由 = /projects)时发生,但在使用控制器操作 backToMyProjects 从带有查询的路由返回到非查询路由时会发生。
  • 什么版本的 ember-data?从 1.13 开始,findAll accepts reload: true

标签: ember.js ember-data


【解决方案1】:

else 条件下,再次使用find() 而不是findAll(),后者从商店获取所有内容:

return this.store.find('project');

更新:没关系,在 1.11 及更高版本中,无论如何这都会在后台调用 findAll()。不知道如何强制它不使用商店。

到目前为止,我已经将 unloadAll() 包装在 Ember.run 中,它似乎可以工作,但我不确定为什么这是必要的:

  model: function(params) {
    if (params.q) {
      return this.store.find('project', params);
    } else {
      var _this = this;
      Ember.run(function() {
        _this.store.unloadAll('project');
      });
      return this.store.find('project');
    }
  }

【讨论】: