坚持绑定财产变化的模型

时间:2014-08-04 15:51:03

标签: javascript performance ember.js debouncing

当其中一个属性绑定到模板输入时,立即持久化模型的最佳做法是什么?在您看来,它属于模型还是控制器?

我想出了一个基于观察者的解决方案:

# Models
App.Foo = DS.Model.extend
  bars: DS.hasMany('bars')

App.Bar = DS.Model.extend
  quantity: DS.attr('number')

# Template
{{#each bar in bars}}
  {{input value=bar.quantity}}
{{/each}}

# Controller
persistQuantity: ( ->
  @get('bars').forEach (bar) -> bar.save() if bar.get('isDirty')
).observes('bars.@each.quantity')

但是由于某种原因,这会激发多个(对我来说是3个)保存对同一模型的请求。

我也尝试将观察者放在模型上,但这是无休止的循环:

# App.Bar Model
  persistQuantity: ( ->
    @save()
  ).observes('quantity')

我试图通过Ember.run.once解决这个问题,但我对Ember跑圈的理解显然不够深。

1 个答案:

答案 0 :(得分:1)

它所属的位置取决于您是否希望模型在更改时保存,或仅在特定视图更改时保存。如果您希望模型始终保存,无论保存在何处,都可以在模型上进行保存。如果要控制从特定视图中保存它,请在控制器中执行此操作。

Debouncing将是解决多重呼叫问题的最佳选择。观看特定项目,然后在更改时自动保存。您还可以观看isDirty并在其发生变化时触发,但我更喜欢其他模式(尽管isDirty规模更好,信息量更少)。这是两种模式,可以随意混合搭配。

让脏模型自动保存:

App.Bar = DS.Model.extend
  quantity: DS.attr('number'),
  watchDirty: function(){
    if(this.get('isDirty')){
      this.save();
    }
  }.observes('isDirty')

示例:http://emberjs.jsbin.com/OxIDiVU/898/edit

在项目变脏(或多个项目)时保存模型队列

App.Bar = DS.Model.extend({
    quantity: DS.attr(),  
    watchQuantity: function(){
      if(this.get('isDirty')){
        Em.run.debounce(this, this.save, 500); 
      }
    }.observes('quantity')
});

示例:http://emberjs.jsbin.com/OxIDiVU/897/edit