Attributes, options, and properties

When we talk about attributes in Backbone, they often sound similar to regular JavaScript properties. After all, both attributes and properties are key-value pairs stored on a Model object. The difference between the two is that attributes aren't (in a technical sense) actually properties of a Model at all; instead, they are the properties of a property of a Model. Each Model class has a property called attributes, and the attributes themselves are stored as properties of that attributes property. Take an example of the following code snippet:

var book = new Backbone.Model({pages: 200});
book.renderBlackAndWhite = true;
book.renderBlackAndWhite // is a property of book
book.attributes.pages; // is an attribute of book
book.attributes.currentPage = 1; // is also an attribute of book}

Note

Attributes versus Properties

As shown in the preceding code snippet, Backbone's Models class can also have regular, nonattribute properties. If you need to store a piece of data in a Model, you can choose between using a property or an attribute. In general, you should use an attribute only when the data is going to be synced to the server or when you want other parts of your code to be able to listen for data changes. If your data doesn't meet these requirements, it's best to store it as a regular JavaScript property instead of as an attribute, because storing such data as an attribute will create more work for you when you save the Model class.

On a purely conceptual level, any of the core persistent information that a Model class is designed to hold belongs in its attributes, while any information that is secondary or derived, or which is only designed to last until the user refreshes the page, should be stored as properties.

If you want to pass in attributes when you create a new Model class, you can simply provide them as the first argument and Backbone will automatically add them. You can also define default attributes, which all new Models of that class will have, using the defaults property when you extend your Model class, as shown here:

var Book = Backbone.Model.extend({

    defaults: {publisher: 'Packt Publishing'}
});
var book = new Book();
book.attributes.publisher; // 'Packt Publishing'

It is important to remember, however, that in JavaScript, objects are passed by reference, which means that any object you provide in defaults will be shared with, not copied between, instances of your Model class. In other words, check out the following code snippet:

var Book = Backbone.Model.extend({
    defaults: {publisher: {name: 'Packt Publishing'}}
});
var book1 = new Book();
book1.attributes.publisher.name // == 'Packt Publishing'
var book2 = new Book();
book2.attributes.publisher.name = 'Wack Publishing';
book1.attributes.publisher.name // == 'Wack Publishing'!

Since you probably don't want changes to one Model affecting your other Models, you should avoid setting objects in defaults. If you really need to set an object as a default, you can do so in the Model's initialize method or by using a more advanced function-based form of defaults, which we'll cover later on in Chapter 7, Fitting Square Pegs in Round Holes – Advanced Backbone Techniques.

While setting default attributes for Models is easy, the same cannot be said about adding default direct properties to a Model when it is first created. The best way to set these properties is to use the Model's initialize method. For instance, if you want to set a renderBlackAndWhite property when you create a Book Model, you can do what is described in the following code snippet:

var Book = Backbone.Model.extend({
    initialize: function(attributes, options) {
        this.renderBlackAndWhite =  options.renderBlackAndWhite;
    }
});

The preceding code sets the renderBlackAndWhite property of each newly created book to the renderBlackAndWhite option passed in when the book is created.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.145.152.242