Backbone.stickit 和 html-form:如何只保存(补丁)更改的属性?

Posted

技术标签:

【中文标题】Backbone.stickit 和 html-form:如何只保存(补丁)更改的属性?【英文标题】:backbone.stickit and html-form: How to save (patch) only changed attributes? 【发布时间】:2014-03-21 18:22:37 【问题描述】:

tl;dr

如何使用带有 html 表单的主干.stickit 来更改从服务器获取的现有模型,并且仅 PATCH 更改的属性(由 html 表单中的用户输入更改)到服务器?

/tl;dr

我在backbone.js 应用程序中使用backbone.stickit 将模型绑定到作为主干视图一部分的HTML 表单。到目前为止,这工作正常,但如果我要保存绑定模型,它会变得有点复杂。这是因为我想使用 PATCH 方法并且只将更改的属性发送到服务器。我试图说明我到目前为止所做的事情:

从服务器获取模型

user = new User(); //instatiate a new user-model
user.fetch(); //fetching the model from the server

console.log(user.changedAttributes()); // Returns ALL attributes, because model was empty

最后一行表示我的问题,因为我认为我可以稍后使用changedAtrributes() 方法来获取需要在服务器上打补丁的属性。所以我尝试了这个我发现的解决方法here

user.fetch(
    success: function (model, response, options) 
        model.set();
    
);

user.changedAtrributes(); //Returns now "false"

做stickit-bindings

现在我渲染我的视图并在视图上调用stickit() 方法来进行绑定:

//Bindings specified in the view:
[...]
bindings: 
  "#username" : "username"
  "#age"      : "age"


[...]

//within the render method of the view
this.stickit();

绑定工作正常,我的用户模型得到更新,但 changedAttributes() 始终为空。

将模型保存到服务器

如果用户已完成所有必要的更改,则应将模型保存到服务器。我想使用 PATCH 方法,只将更改后的属性发送到服务器。

user.save(null, patch:true); //PATCH method is used but ALL attributes are sent to the server

user.save(user.changedAttributes(),patch : true); 

第二种方法有不同的结果:

    如果我没有使用 user.set() 解决方法,所有属性都会被修补到服务器 如果我使用user.set() woraround,changedAttributes() 的返回值为“false”并且所有属性都被 PUT 到服务器 如果我在调用save() 之前调用user.set("age","123"),那么只有年龄属性会被修补到服务器

所以结果 3 是我想要的行为,但这有两个问题:首先,如果在 html 表单中更改属性,stickit 似乎没有在模型上使用 set() 方法来更新属性。其次,如果你用一个属性调用set(),然后用另一个属性调用,changedAttributes() 只会返回第二个属性。

也许我只是监督了主干或主干.stickit 文档中的某些内容,所以我没有得到所需的行为。有什么想法吗?

【问题讨论】:

【参考方案1】:

注意:发现问题与backbone.stickit没有直接关系,更多的是与主干本身有关。

我自己解决了这个问题,也许这可以帮助可能偶然发现这个问题的人:

Backbone 只跟踪 unchanged 属性,但不跟踪 unsaved 属性。所以用

model.changedAttributes();

你只会得到模型的属性,这些属性自上次改变后

model.set("some_attribute","some_value")

最后我偶然发现了backbone.trackit,这是一个由主干.stickit 的创建者维护的主干.js 插件。使用此插件,您可以跟踪 未保存 属性(自上次 model.save() 以来已更改的所有属性),然后在模型的保存方法中使用它们。示例(我的用例):

Backbone.View.extend(
  bindings: 
    "#name" : "name",
    "#age"  : "age"
  ,

  initialize: function () 
    this.model = new User();
    this.model.fetch(
      success: function (model, response, options) 
        //this tells backbone.stickit to track unsaved attributes
        model.startTracking(); 
      
    );
  ,

  render: function () 
    this.$el.html(tmpl);
    this.stickit();
    return this;
  ,

  onSaveUserToServer: function () 
    //first argument: only unsaved attributes, second argument: tell backbone to PATCH
    this.model.save(this.model.unsavedAttributes(),  patch: true );
  );

);

【讨论】:

以上是关于Backbone.stickit 和 html-form:如何只保存(补丁)更改的属性?的主要内容,如果未能解决你的问题,请参考以下文章

Backbone.stickit 和 html-form:如何只保存(补丁)更改的属性?

为 Backbone.Stickit.js 绑定设置全局 setOptions

在 Backbone Stickit 中结合使用 visible 和 onGet

如何让backbone.stickit 一次收集所有值?

模型未在表单提交时更新,使用 Backbone + Stickit

Backbone stickit - 使用类名和限定的“this”绑定