Search code examples
jquerybackbone.jsbackbone-views

Model destroy returning undefined is not a function


I'm trying to destroy a model and I get "Uncaught TypeError: undefined is not a function" when I call this.model.destroy({options})

My model is like this:

    window.CompanyModel = Backbone.Model.extend({

        initialize: function() {
            console.log('CompanyModel:initialized');
        },

        parse: function(response, options) {
            return response;
        },

    });

Collection:

    window.CompaniesCollection = Backbone.Collection.extend({

        model: window.CompanyModel,

        initialize: function() {
            console.log('CompaniesCollection:initialized');
        },  
    });

View:

    window.CompaniesView = Backbone.View.extend({
         initialize : function() {
             console.log('CompaniesView:initialized');
             this.companies = new CompaniesCollection();
             this.companies.url = function(id) {
                 return '../src/rest/administration/companies/companies';
             };
             this.company = new CompanyModel();
         },
         [...more code...]
         confirmDeleteForm : function(event) {
             event.preventDefault();

             var company_id = $('#company_existing').val();
             var self=this;
             this.company = this.companies.where({'company_id':company_id});

             this.company.destroy({
                 wait: true,
                 success: function(model, response) {
                     console.log('deleted');
                     $('#deleteModal').modal('hide');
                     self.cleanForm();
                     self.getCompanies();
                 },
                 error: function(model, response) {
                     console.log('error');
                     console.log(model);
                     console.log(response);
                     console.log(options);
                     if (response.status == 500) {
                        self.showErrorMessage('Se produjo un error en el servidor', 'ERROR');
                     } else {
                        self.showErrorMessage(response.responseText, 'ATENCION');
                     }
                }
           });

       },

Any help would be appreciated.

REgards, LN


Solution

  • this.companies.where returns an array, from the fine manual:

    where collection.where(attributes)

    Return an array of all the models in a collection that match the passed attributes.

    That means that this:

    this.company = this.companies.where({'company_id':company_id});
    

    leaves an array in this.company and arrays don't have destroy methods.

    If there is only one entry in this.companies that matches {company_id: company_id} then you could say:

    this.company = this.companies.where({'company_id':company_id})[0];
    // -----------------------------------------------------------^^^
    

    or you could use findWhere:

    findWhere collection.findWhere(attributes)

    Just like where, but directly returns only the first model in the collection that matches the passed attributes.

    and say:

    this.company = this.companies.findWhere({'company_id':company_id});
    

    If that's the case then your company_id attribute is probably really the unique identifier for companies and then you might want to set the idAttribute in your model to company_id:

    window.CompanyModel = Backbone.Model.extend({
        idAttribute: 'company_id',
        //...
    

    so that you could use Collection#get to find it without searching.