Json 主干线不撕裂

Json 主干线不撕裂,json,backbone.js,model,render,Json,Backbone.js,Model,Render,我是Backbone.js的一个完整的n00b,只使用了几天。我试图获取JSON数据来填充模型,在这个场景中,我需要生成两个模型。以下是我一直使用的JSON示例: JSON 主干JS // MODEL var Service = Backbone.Model.extend({ defaults: { id: '', name: '', label: '', description: '', dateAdded: '', dateModified:

我是Backbone.js的一个完整的n00b,只使用了几天。我试图获取JSON数据来填充模型,在这个场景中,我需要生成两个模型。以下是我一直使用的JSON示例:

JSON

主干JS

// MODEL
var Service = Backbone.Model.extend({
defaults: {
    id: '',
    name: '',
    label: '',
    description: '',
    dateAdded: '',
    dateModified: ''
}
});
var service = new Service();

// COLLECTION
var ServiceList = Backbone.Collection.extend({
    model: Service,
    url: "./api/service.php",
    parse: function(response) {
        return response.items;
    }
});
//
var serviceList = new ServiceList();
var jqXHR = serviceList.fetch({
    success: function() {
        console.log("Working!");
                console.log(serviceList.length);
    },
    error: function() {
        console.log("Failed to fetch!");
    }
});


// VIEW for each Model
var ServiceView = Backbone.View.extend({
    el: $('.widget-content'),
    tagName: 'div',
    template: _.template($('#service-template').html()),
    initialize: function() {
        this.collection.bind("reset", this.render, this);
    },
    render: function() {
        console.log(this.collection);
        this.$el.html('');
        var self = this;
        this.collection.each(function(model) {
            self.$el.append(self.template(model.toJSON()));
        });
        return this;
    }
});
//
var serviceView = new ServiceView({
    collection: serviceList
});
console.log(serviceView.render().el);
html


当我在控制台上记录serviceList.length时,我得到了值2,因此我相信JSON对象已成功获取。我也得到了成功的“工作”回应。但是,在视图中,我显示了一个空对象,这给了我一个空模型


我仍在努力理解做这件事的最佳方式。也许我应该为“项”使用集合,然后为每个模型数据映射集合?我做错了什么?非常感谢任何建议或帮助。

调用
serviceList.fetch
是异步进行的,因此当您尝试
console.log(serviceList.length)时服务器尚未发送响应,这就是为什么会得到值1,请尝试以下操作:

var list = serviceList.fetch({
    success: function() {
        console.log(serviceList.length);
        console.log("Working!");
    },
    error: function() {
        console.log("Failed to fetch!");
    }
});

我可以看到两个问题。首先,要删除
serviceList.reset(list)
。您的集合应该通过调用
fetch
自动填充。(在任何情况下,
fetch
的返回值都不是来自服务器的数据结果,而是“jqXHR”对象)

其次,您可能希望将
serviceList
实例作为其“集合”传递到视图中。实际上,您正在将一个空模型实例传递到视图中

var serviceView = new ServiceView({
    collection: serviceList
});
对于视图,使用集合进行渲染:

var ServiceView = Backbone.View.extend({
    // ...

    initialize: function() {
        // render when the collection is reset
        this.collection.bind("reset", this.render, this);
    },
    render: function() {
        console.log("Collection rendering: " + JSON.stringify(this.collection.toJSON()));

        // start by clearing the view
        this.$el.html('');            

        // loop through the collection and render each model
        var self = this;
        this.collection.each(function(model) {
            self.$el.append(self.template(model.toJSON()));
        });
        return this;
    }
});

小提琴演示。

感谢您澄清了对提琴的理解。我看到JSFIDLE确实可以工作,但在复制时,我仍然得到一个空模型。我不明白为什么您建议删除serviceList重置,但将其添加到JSFIDLE?@user3362859我将其添加到FIDLE中,就像一个模拟一样——通常您在手头已有数据时使用
collection.reset
,然后使用
collection.fetch
向服务器发送请求。不过,你不需要两者都用……这是有道理的。我看到jqXHR有我们获取的存储数据,但我没有看到它被传递到集合中。这可能是模型仍然为空的原因。我需要将jqXHR传递到集合中吗?我更新了帖子以显示我的代码和您的修订版。您能看到导致空模型的原因吗?@user3362859是的——您示例中的“服务”对象只是一个空模型。它与提取到“serviceList”集合中的数据完全没有连接。
var serviceList = new ServiceList();
var jqXHR = serviceList.fetch({
    success: function(collection, response) {
        console.log("Working!");

        // this is the asynchronous callback, where "serviceList" should have data
        console.log(serviceList.length);
        console.log("Collection populated: " + JSON.stringify(collection.toJSON()));
    },
    error: function() {
        console.log("Failed to fetch!");
    }
});
// here, "serviceList" will not be populated yet
var serviceView = new ServiceView({
    collection: serviceList
});
var ServiceView = Backbone.View.extend({
    // ...

    initialize: function() {
        // render when the collection is reset
        this.collection.bind("reset", this.render, this);
    },
    render: function() {
        console.log("Collection rendering: " + JSON.stringify(this.collection.toJSON()));

        // start by clearing the view
        this.$el.html('');            

        // loop through the collection and render each model
        var self = this;
        this.collection.each(function(model) {
            self.$el.append(self.template(model.toJSON()));
        });
        return this;
    }
});