最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Backbone.js: Uncaught TypeError: Object #<Object> has no method 'get' - Stack Overflo

programmeradmin3浏览0评论

Hi I have a Collection which uses fetch() to do the initial fetch from the API. On a user's interaction, a second fetch is triggered, but instead of using the original fetch(), I used a fetchNew() that I defined myself:

Collection

ListingCollection = Backbone.Collection.extend({
    model: Listing,
    url: '/api/search_by_bounds',

    fetchNew: function(options) {
        options = options || {};
        var collection = this,
            success = options.success;
        options.success = function(resp, status, xhr) {
            _(collection.parse(resp, xhr)).each(function(item) {
                // added this conditional block
                if (!collection.get(item.id)) {
                    // Update collection
                    collection.add(item, {silent:true});
                    // Render View
                    new ListingMarkerView({ model:item }).render();
                }
            });
            if (!options.silent) {
                collection.trigger('reset', collection, options);
            }
            if (success) success(collection, resp);
        };
        return (this.sync || Backbone.sync).call(this, 'read', this, options);
    }
});

This will add only the new Models to the collection, and render only the Views of these new Models. (if all the Views are removed and re-rendered, it will cause a flicker)

View

ListingMarkerView = Backbone.View.extend({

    render: function() {
        var marker = L.marker([this.model.get('lat'), this.model.get('lng')]);
        markers.addLayer(marker);
    },

    close: function() {
        this.unbind;
    }

});

Error

However I am getting an error:

Uncaught TypeError: Object #<Object> has no method 'get' 

which corresponds to this line in ListingMarkerView

var marker = L.marker([this.model.get('lat'), this.model.get('lng')]);

Debug

If I were to place a console.log(item) before the line that renders ListingMarkerView

console.log(item)
new ListingMarkerView({ model:item }).render();

I do see a valid item:

Object
    id: "2599084"
    lat: "42.276852"
    lng: "-71.165421"
    price: "2850"
    __proto__: Object

So...

Question

What seems to be the problem? How can this be solved? Thank you!

Hi I have a Collection which uses fetch() to do the initial fetch from the API. On a user's interaction, a second fetch is triggered, but instead of using the original fetch(), I used a fetchNew() that I defined myself:

Collection

ListingCollection = Backbone.Collection.extend({
    model: Listing,
    url: '/api/search_by_bounds',

    fetchNew: function(options) {
        options = options || {};
        var collection = this,
            success = options.success;
        options.success = function(resp, status, xhr) {
            _(collection.parse(resp, xhr)).each(function(item) {
                // added this conditional block
                if (!collection.get(item.id)) {
                    // Update collection
                    collection.add(item, {silent:true});
                    // Render View
                    new ListingMarkerView({ model:item }).render();
                }
            });
            if (!options.silent) {
                collection.trigger('reset', collection, options);
            }
            if (success) success(collection, resp);
        };
        return (this.sync || Backbone.sync).call(this, 'read', this, options);
    }
});

This will add only the new Models to the collection, and render only the Views of these new Models. (if all the Views are removed and re-rendered, it will cause a flicker)

View

ListingMarkerView = Backbone.View.extend({

    render: function() {
        var marker = L.marker([this.model.get('lat'), this.model.get('lng')]);
        markers.addLayer(marker);
    },

    close: function() {
        this.unbind;
    }

});

Error

However I am getting an error:

Uncaught TypeError: Object #<Object> has no method 'get' 

which corresponds to this line in ListingMarkerView

var marker = L.marker([this.model.get('lat'), this.model.get('lng')]);

Debug

If I were to place a console.log(item) before the line that renders ListingMarkerView

console.log(item)
new ListingMarkerView({ model:item }).render();

I do see a valid item:

Object
    id: "2599084"
    lat: "42.276852"
    lng: "-71.165421"
    price: "2850"
    __proto__: Object

So...

Question

What seems to be the problem? How can this be solved? Thank you!

Share Improve this question edited Sep 29, 2012 at 18:47 Nyxynyx asked Sep 29, 2012 at 18:27 NyxynyxNyxynyx 63.7k163 gold badges507 silver badges856 bronze badges 9
  • I'd rather go with usual .reset, why do you want to do that? Can you post a link to the working site so I can inspect? – Michał Miszczyszyn Commented Sep 29, 2012 at 18:39
  • Will .reset remove the items that were in the initial fetch() but not in the subsequent call? I wish to just append new models to the collection without removing the old ones. – Nyxynyx Commented Sep 29, 2012 at 18:42
  • If you want to add new ones without removing old ones, use fetch({add:true}). However you should still understand the answer I gave to your question, since it will definitely e up elsewhere. – blockhead Commented Sep 29, 2012 at 18:46
  • Yes fetch{add:true}) has the effect that I want, thanks! However, I still cant render the View after using _.bindAll – Nyxynyx Commented Sep 29, 2012 at 18:50
  • Again: Can you post a link to the working site so I can inspect? – Michał Miszczyszyn Commented Sep 29, 2012 at 18:54
 |  Show 4 more ments

1 Answer 1

Reset to default 6

The problem is render does not have this defined correctly. Add a initialize method in the view class like this:

initialize: function() {
   _.bindAll(this); //Make all methods in this class have `this` bound to this class
}
发布评论

评论列表(0)

  1. 暂无评论