AndraD
AndraD

Reputation: 2850

Backbone model.destroy(): Is explicit removal from collection necessary?

I have a simple question. I am looking at a function with 2 lines of code:

deleteTask: function() {
    this.parent.collection.remove(this.model);
    this.model.destroy();
}

If I comment out the first line, which is supposed to remove the model from its collection, things seem to work as intended (as in, the model is removed automatically). From Backbone's website, this is the relevant discription for a model's "destroy" function:

Triggers a "destroy" event on the model, which will bubble up through any collections that contain it.

Am I safe to assume that the removal of this.parent.collection.remove(this.model); will not affect the functionality of the code in any way? This is what I think, but I wanted to make sure of it.

Thank you!

Upvotes: 25

Views: 35949

Answers (2)

user2794365
user2794365

Reputation: 13

The solution is to override the Backbone model destroy function. I made this on an abstract model with success and callback strategy:

Parameter "data" corresponds to the original parameter "resp".

destroy: function(successCallback, errorCallback) 
{
    var options = { wait: true };
    var model = this;

    successCallback = successCallback || function() {};
    errorCallback = errorCallback || function() {};               

    var destroy = function() 
    {
        model.trigger('destroy', model, model.collection, options);
    };

    options.success = function(data) 
    {
        if ('SUCCESS' === data.responseCode)
        {
            if (options.wait || model.isNew())
                destroy();

             successCallback(data);

            if (!model.isNew())
                model.trigger('sync', model, data, options);
        }
        else
        {
            errorCallback(data);
        }
    };

    if (this.isNew()) 
    {
        options.success();
        return false;
    }

    var xhr = this.sync('delete', this, options);

    if (!options.wait)
        destroy();

    return xhr;
}

Upvotes: -3

asgeo1
asgeo1

Reputation: 9078

If you destroy a model, it is removed from any collections that was containing it. You can see that in the backbone source

//Internal method called every time a model in the set fires an event.
_onModelEvent: function(event, model, collection, options) {
    ...
    if (event === 'destroy') this.remove(model, options);

So yes, I wouldn't think you would need to remove the model from your collection explicitly.

But don't trust me, test for yourself :)

deleteTask: function() {
    that = this;
    this.model.destroy({
      success: function() {
        console.log(that.parent.collection);
      }
    });
}

Check the console for yourself to see whether the model was removed from the collection.

Upvotes: 36

Related Questions