Michael Joseph Aubry
Michael Joseph Aubry

Reputation: 13422

Backbone.js why do I have to use underscore (_.each) to target the model?

So whenever I want to select a model from my collection I always use backbone's very own where method.

var homeTeam = this.collection.where({teamName: this.currentTeamName('home')});

I have my own method that grabs the current team and I pass "home" or "away" as an argument, and it knows which model to grab, this is all fine and dandy, another example would be to just pass a string like below.

// This is practically the same as the above.
var homeTeam = this.collection.where({teamName: 'bulls'});

So if I log that variable console.log(homeTeam) the console shows that model, just like it does any model.

The console shows me I have access to regular methods a model can use http://backbonejs.org/#Model but if I call one of those methods I get an error, ex homeTeam.save({someAttr: 'juicy'});

So I just use underscore's each method like below, and it works.

_.each(homeTeam, function(model) { model.save({someAttr: 'juicy'}); }, this);

I have been doing this for awhile but I am curious to know why I must do that, when logging the homeTeam it passes the model just like

_.each(homeTeam, function(model) { console.log(model) }, this); 

they show up exactly the same in the console.

Upvotes: 0

Views: 103

Answers (3)

marionebl
marionebl

Reputation: 3382

Assuming team.teamName is unique you could safely use .findWhere, which returns a single model from your collection instead of .find, which returns an array of models.

From the underscore docs:

findWhere Looks through the list and returns the first value that matches all of the key-value pairs listed in properties.

as opposed to

where Looks through each value in the list, returning an array of all the values that contain all of the key-value pairs listed in properties.

Upvotes: 1

linstantnoodles
linstantnoodles

Reputation: 4400

Because where returns an array of models. The array is not a model object. It's an array.

See source.

Upvotes: 1

Russ Clarke
Russ Clarke

Reputation: 17909

Ahh, I think I see the problem here.

.where returns an Array; Even though it's an array of Model, the Javascript console will evaluate the entry as a model so you can see the methods that Backbone provides.

What you need to do is use .findWhere.

This will return the first matching model, as a correctly typed object.

Alternately you could try (just to prove) 'homeTeam[0].save(...)

To clarify: you're getting the error because homeTeam is not what you think it is; welcome to Javascript!

Upvotes: 1

Related Questions