override Backbone's Collection-fetch

2019-02-02 04:07发布

问题:

I want to get my collection in a NON-RESTful way, so I decide to override the Collection.fetch with

App.carClc = Backbone.Collection.extend({
    model : App.cardModel,
    url : 'http://localhost/bbtest/data.php',
    fetch : function() {
        $.ajax({
            type : 'GET',
            url : this.url,
            success : function(data) {
                console.log(data);
            }
        });
    }
});

I don't know how to set my collection to the response. I'm new to BackboneJS, thanks all of you!

回答1:

If you want to add a custom "decorator" to fetch, but not override it completely, try:

    var MyCollection = Backbone.Collection.extend({

        //custom methods

        fetch: function(options) {

            //do specific pre-processing 

            //Call Backbone's fetch
            return Backbone.Collection.prototype.fetch.call(this, options);
        }

  });    

Here, you don't have to roll out your own $.ajax

Also, don't forget the return in the last line if you want to use the jQuery promise returned by Backbone's fetch method.

See http://japhr.blogspot.in/2011/10/overriding-url-and-fetch-in-backbonejs.html for more details.



回答2:

Backbone collection has two methods to set new data add and reset. Let's say you want to replace all collection data with the incoming data and therefor use the reset:

 App.carClc = Backbone.Collection.extend({
model : App.cardModel,
url : 'http://localhost/bbtest/data.php',
fetch : function() {
    // store reference for this collection
    var collection = this;
    $.ajax({
        type : 'GET',
        url : this.url,
        dataType : 'json',
        success : function(data) {
            console.log(data);
            // set collection data (assuming you have retrieved a json object)
            collection.reset(data)
        }
    });
}
})


回答3:

I am using something like this:

$.when( $.ajax( URL, { dataType: "json" } ) )
    .then( $.proxy( function( response ) {
            ctx.view.collection.reset( response );                              
    },ctx ) );

The main point beeing I use collection.reset(data) to reinitialize the collection



回答4:

If you would like to keep fetch "thenable" for promises then you could also do something like this:

fetch: function() {
    var self = this,
        deferred = new $.Deferred();

    $.get(this.url).done(function(data) {
            // parse data
        self.reset({parsed data});
        deferred.resolve(); //pass in anything you want in promise
     });
     return deferred.promise();
}


回答5:

If you need to do this for every model and/or collection, override Backbone.ajax.

Overriding Backbone.ajax gives you the request options that would be normally passed to $.ajax. You only need to return the response of $.ajax (or some other Promise) and don't need to worry about setting stuff in the collection/model.