使用Backbone并尝试使用来自Parse.com的数据填充我的集合

时间:2015-06-16 01:13:27

标签: backbone.js collections parse-platform

这里对Backbone很新。我试图重新创建ToDo示例,而不复制和粘贴我遇到的教程中的代码。我也使用Parse.com作为我的后端。我坚持尝试使用Backbone View使用待办事项填充我的收藏。这是我的观点...

app.ItemsView = Backbone.View.extend({

    tagName: "section",

    initialize: function() {
        app.items = new app.ItemCollection;
        app.items.query = new Parse.Query(app.Item);
        app.items.fetch();

        console.log(app.items.models.length);

        var itemsInJSON = [];

        app.items.models.forEach(function(item){
            console.log("Item being pushed is " + item);
            itemsInJSON.push(item.toJSON());
        });

        this.render(app.items);
    },

    render: function(items) {
        items.each(this.addItem, this);
        return this;
        // $("#bucketList").html(itemsView.render().el);
    },

    addItem: function(item) {
        var itemView = new app.ItemView ({model: item});
        this.$el.append(itemView.render().el)
    }

});

我已经在Parse.com上查看了我的应用程序,我可以看到我的数据库中保存了2个项目。我知道存在问题,因为当我在初始化时调用console.log(app.items.models.length);时,我的长度为0.但是当我在页面加载后直接在Chrome开发工具控制台中键入app.items.models.length时,我得到了一个长度为2。

为什么我的初始化没有提取项目来填充我的收藏?

2 个答案:

答案 0 :(得分:0)

由于fetch实际上是在执行AJAX请求,因此它是异步的,您必须处理这个事实。它会返回一个jqXHR对象,如docs中所述,因此您的代码应该执行类似的操作

app.items.fetch().then(function() {
  console.log(app.items.models.length);
  ...
  this.render();
}.bind(this));

这确保了依赖于AJAX请求结果的代码仅在该请求完成后才会执行。

请注意,我使用.bind(this)来确保在jqXHR承诺的回调中我可以以this的形式访问该视图。这仅适用于IE9 +(请参阅MDN),如果您需要支持IE8或更低版本,请使用下划线_.bind

答案 1 :(得分:0)

在这种情况下,我建议你不要在承诺中使用Jquery。 在这种情况下,Backbone使用事件来管理/帮助。

你应该做的第一件事是将模型/集合逻辑(fetch,set,get等)移到模型/集合中

然后你可以在你的视图中找到这样的东西:

this.lintenTo(app.items, "sync", this.render);

这是处理这些情况的主要方式。

但为什么不使用Promises?

当你在视图中执行fetch()时,你已经打破了SRP,因为如果由于某种原因将来你需要改变调用fetch的方式,你需要触摸视图文件,但请记住,fetch是一个模型/集合函数,在我看来,这意味着视图有多个改变的原因。此外,当您在视图中执行fetch()并使用promises时,您需要使用bind(this)来保留范围,在我看来,您可以避免它只是将此代码传递给模型/集合并只是在视图中侦听事件。 对于任何模型/集合函数(获取,保存,销毁,设置,获取......)都是一样的。