21

我有一个应用程序,它目前包含同一模型的对象的视图。它们从服务器检索,循环并使用 add 方法添加到列表控制器

<script>
App.Controllers.List = Em.ArrayProxy.create({
  content: Ember.A([]),
  add: function(obj){
    this.pushObject(obj);
  }
});
</script>

我现在正在处理用户创建一个新对象(在通过验证后)将被添加到列表并发送到服务器的部分。

我找不到任何关于通过输入表单创建新对象的最佳模式的示例。我可以看到一些选项,并且已经半实现了一些,但感觉都不对。

  • 创建一个带有适当表单元素的视图和一个使用 .get() 从表单元素中检索到的各种属性来实例化模型的方法
  • 在视图的内容中创建一个模型并将表单元素绑定到该模型。在视图中包含一个用于添加到控制器阵列/保存到服务器的方法
  • 创建一个模型,将其添加到控制器数组并打开它进行编辑

我可以拼出我想要的功能,但我更愿意确保我了解最佳实践。

我目前有这样的东西(这是我列表中的第二个项目符号)

<script>
App.Views.ItemCreate = Em.View.extend({
  content: App.Models.Item.create({}),
  templateName: 'create',
  createButton: function(){

    var itemObj = this.get('content');
    var item = {};
    item.title = this.get('content').get('title');

    $.ajax({
      type: 'POST',
      url: '/test/data.json',
      data: item,
      dataType: 'json',
      success: function(responseData, textStatus, jqXHR) {
        App.Controllers.List.add(itemObj);
      }
    });
  }
});
</script>

<script type="text/x-handlebars" data-template-name="create">
  {{view Em.TextField id="create-title" valueBinding="content.title"}}
  <a href="#" {{action "createButton" }}>Create</a>
</script>

非常感谢任何帮助

笔记

我已将正确答案更改为 pangratz 的。虽然其他回复直接回答了我的问题,但我相信那些通过谷歌找到这个的人应该参考 Pangratz 提供的答案,因为它不仅是好的 MVC,而且更像是 Ember-y :o)

4

2 回答 2

23

与服务器通信绝对是视图中不应该做的事情。这是控制器的用途。为了进一步分离应用程序的不同部分,我什至会考虑实现一个DataSource处理 AJAX 请求的方法。这种拆分使您的应用程序更具可测试性,并且每个组件都可重用。然后通过绑定来实现视图、控制器和数据源的具体连接。

您的案例的工作流程可能如下:

  • 该视图显示您的编辑表单,其中的值绑定到控制器
  • 视图处理一个保存动作,告诉控制器保存创建的对象
  • 控制器将保存委托给 DataSource,然后最终启动 AJAX 请求
  • 保存对象时通知控制器

您还应该查看ember-data,它是客户端数据存储并为您处理所有样板文件。还可以看看Ember.js 应用程序的架构 - 数据EmberJS:在相当复杂的应用程序中很好地分离模型、商店、控制器、视图的关注点?


看法:

App.View.ItemCreate = Ember.View.extend({
  templateName: 'create',
  createObject: function(evt) {
    var object = this.get('content');
    var controller = this.get('controller');
    controller.createObject(object);
  }
});

控制器:

App.Controllers.List = Ember.ArrayProxy.extend({
  content: [],
  createObject: function(hash) {
    var dataSource = this.get('dataSource');
    dataSource.createObject(hash, this, this.createdObject);
  },
  createdObject: function(object) {
    this.pushObject(object);
  }
});

数据源:

App.DataSource = Ember.Object.extend({
  createObject: function(hash, target, callback) {
    Ember.$.ajax({
      success: function(data) {
        callback.apply(target, data);
      }
    });
  }
});

把所有东西粘在一起:

App.dataSource = App.DataSource.create();
App.listController = App.Controllers.List.create({
  dataSourceBinding: 'App.dataSource'
});

App.View.ItemCreate.create({
  controllerBinding: 'App.listController'
}).append();
于 2012-04-20T14:56:47.247 回答
2

如果你想遵循严格的 MVC 模型,那么模型不应该在视图上创建,而是在控制器上创建。Ember 还很年轻,还没有任何定义的模式,我要做的就是将您的模型设置为视图的内容(正如您已经完成的那样),所有输入都绑定到不同的模型属性。然后当按下按钮时:

createButton: function(){
  App.Controllers.List.create(this.get('content')); 
}

在控制器上:

create: function(model) {
  if model.valid() { //validates the model
    model.save({
      onSuccess: function(response) { // callback
        var item = App.Models.Item.create(response.item)
        App.controllers.List.add(item)
      }
    })
  }

最后是模型:

save: function(options) {
  $.ajax({
    type: 'POST',
    url: '/test/data.json',
    data: item,
    dataType: 'json',
    success: options.onsuccess
  });
}

这是其他 js 框架期望您工作的方式。感觉有点冗长和复杂,但它使事情保持在原位

于 2012-04-20T12:47:49.810 回答