Wednesday, December 11, 2013

Tutorial: HTML Templates with Mustache.js

}
When developing modern HTML applications, you often write a lot of HTML fragments programmatically. You concatenate HTML tags and dynamic data, and insert the resulting UI markup into the DOM. Here is a random code example of this approach:
1
2
3
4
5
6
7
8
9
$.each(messages.reverse(), function(index, message) {
    $('#messageList').append(
        '
  • '
  • +
            message.userName + '
    ' +
            '+
            message.datePosted + '">
    ' +
            '
    '
    + message.messageText + '
    ');
        }
    });
    The proliferation of this kind of code throughout your application comes with some downsides. The tight coupling of UI and data logic doesn’t promote separation of concerns and reuse. It makes your application harder to write and harder to maintain.

    HTML templates address this issue by decoupling the UI definition (HTML markup) from the data. There are a number of HTML template solutions out there: jQuery Templates, Underscore.js, and Mustache.js to name a few. Mustache.js is a popular choice because of its powerful syntax and fast rendering.
    Mustache is a “logic-less” template syntax. “Logic-less” means that it doesn’t rely on procedural statements (if, else, for, etc.): Mustache templates are entirely defined with tags. Mustache is implemented in different languages: Ruby, JavaScript, Python, PHP, Perl, Objective-C, Java, .NET, Android, C++, Go, Lua, Scala, etc. Mustache.js is the JavaScript implementation.
    In this article, we take a quick tour of some of the capabilities of Mustache.js.
    To start using Mustache.js, simply add a script tag to your html file pointing to mustache.js which is available here.
    You can run all the examples below here.

    Sample 1: Basic Template

    This is a self-explanatory example. Note that:
    • Instead of being defined in a variable, the data often comes from a service call (see sample 2)
    • Instead of being defined in a variable, the template is often read from a file (see sample 3)
    1
    2
    3
    4
    5
    6
    7
    8
    var person = {
        firstName: "Christophe",
        lastName: "Coenraets",
        blogURL: "http://coenraets.org"
    };
    var template = "

    {{firstName}} {{lastName}}

    Blog: {{blogURL}}"
    ;
    var html = Mustache.to_html(template, person);
    $('#sampleArea').html(html);
    Result:

    Christophe Coenraets

    Blog: http://coenraets.org

    Sample 2: Basic Template using Ajax data

    Same as sample 1, except that we get the data from an Ajax service call.
    1
    2
    3
    4
    5
    $.getJSON('json/data.json', function(data) {
        var template = "

    {{firstName}} {{lastName}}

    Blog: {{blogURL}}"
    ;
        var html = Mustache.to_html(template, data);
        $('#sampleArea').html(html);
    });
    Result:

    John Smith

    Blog: http://johnsmith.com

    Sample 3: Externalized Template

    Same as sample 2, except that we read the template from the main HTML file.
    1
    2
    3
    4
    5
    $.getJSON('json/data2.json', function(data) {
        var template = $('#personTpl').html();
        var html = Mustache.to_html(template, data);
        $('#sampleArea').html(html);
    });
    The template is defined as follows in index.html:
    1
    2
    3
    4
    <script id="personTpl" type="text/template">
    <h1>{{firstName}} {{lastName}}</h1>
    <p>Blog URL: <a href="{{blogURL}}">{{blogURL}}</a></p>
    </script>
    Result:

    Lisa Jones


    NOTE: Sample 3 represents the way templates are being used in many dynamic Web applications:
    • You get data from an Ajax service
    • You read the template from an external file
    In the remaining of this article, we declare the data and the template in variables to keep the examples self-contained. Remember to refer to sample 3 for a traditional setup when using templates in a dynamic Web application.

    Sample 4: Enumerable Section

    1
    2
    3
    4
    var data = {name: "John Smith", skills: ['JavaScript', 'PHP', 'Java']};
    var tpl = "{{name}} skills:
      {{#skills}}
    • {{.}}
    • {{/skills}}
    "
    ;
    var html = Mustache.to_html(tpl, data);
    $('#sampleArea').html(html);
    Result:
    John Smith skills:
    • JavaScript
    • PHP
    • Java

    Sample 5: Enumerable Section with Objects

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    var data = {
        employees: [
        {   firstName: "Christophe",
            lastName: "Coenraets"},
        {   firstName: "John",
            lastName: "Smith"}
        ]};
    var template = "Employees:
      {{#employees}}"
    +
                                "
  • {{firstName}} {{lastName}}
  • "
    +
                                "{{/employees}}
    ";
    var html = Mustache.to_html(template, data);
    $('#sampleArea').html(html);
    Result:
    Employees:
    • Christophe Coenraets
    • John Smith

    Sample 6: Nested Objects

    You can use the dot notation to access object properties.
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    var person = {
        firstName: "Christophe",
        lastName: "Coenraets",
        blogURL: "http://coenraets.org",
        manager : {
            firstName: "John",
            lastName: "Smith"
        }
    };
    var template = "

    {{firstName}} {{lastName}}

    {{blogURL}}
    "
    +
                   "Manager: {{manager.firstName}} {{manager.lastName}}";
    var html = Mustache.to_html(template, person);
    $('#sampleArea').html(html);
    Result:

    Christophe Coenraets

    http://coenraets.org
    Manager: John Smith

    Sample 7: Dereferencing

    Same as sample 6, except that we “dereference” the manager object to make it easier to access its properties (without having to use the dot notation).
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    var person = {
        firstName: "John",
        lastName: "Smith",
        blogURL: "http://johnsmith.com",
        manager : {
            firstName: "Lisa",
            lastName: "Jones"
        }
    };
    var tpl = "

    {{firstName}} {{lastName}}

    {{blogURL}}
    "
    +
              "{{#manager}}Manager: {{firstName}} {{lastName}}{{/manager}}";
    var html = Mustache.to_html(tpl, person);
    $('#sampleArea').html(html);
    Result:

    John Smith

    http://johnsmith.com
    Manager: Lisa Jones

    Sample 8: Function

    Templates can reference functions like totalPrice in this example.
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    var product = {
        name: "FooBar",
        price: 100,
        salesTax: 0.05,
        totalPrice: function() {
            return this.price + this.price * this.salesTax;
        }
    };
    var template = "Product Name: {{name}}
    Price: {{totalPrice}}"
    ;
    var html = Mustache.to_html(template, product);
    $('#sampleArea').html(html);
    Result:
    Product Name: FooBar
    Price: 105

    Sample 9: Condition

    Templates can include conditional sections. Conditional sections only render if the condition evaluates to true. A conditional section begins with {{#condition}} and ends with {{/condition}}. “condition” can be a boolean value or a function returning a boolean.
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    var data = {
        employees: [
        {   firstName: "Christophe",
            lastName: "Coenraets",
            fullTime: true,
            phone: "617-123-4567"
        },
        {   firstName: "John",
            lastName: "Smith",
            fullTime: false,
            phone: "617-987-6543"
        },
        {   firstName: "Lisa",
            lastName: "Jones",
            fullTime: true,
            phone: "617-111-2323"
        },
        ]};
    var tpl = "Employees:
      {{#employees}}
    • {{firstName}} {{lastName}}"
    +
              "{{#fullTime}} {{phone}}{{/fullTime}}
    {{/employees}}";
    var html = Mustache.to_html(tpl, data);
    $('#sampleArea').html(html);
    Result:
    Employees:
    • Christophe Coenraets 617-123-4567
    • John Smith
    • Lisa Jones 617-111-2323

    Sample 10: Partials

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    var data = {
        firstName: "Christophe",
        lastName: "Coenraets",
        address: "1 Main street",
        city: "Boston",
        state: "MA",
        zip: "02106"
    };
     
    var template = "

    {{firstName}} {{lastName}}

    {{>address}}"
    ;
    var partials = {address: "{{address}}
    {{city}}, {{state}} {{zip}}"
    };
    var html = Mustache.to_html(template, data, partials);
    $('#sampleArea').html(html);
    Result:

    Christophe Coenraets

    1 Main street
    Boston, MA 02106

    Sample 11: Partials in Enumerable Section

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    var data = { depts: [
        {   name: "Engineering",
            employees: [
                {firstName: "Christophe", lastName: "Coenraets"},
                {firstName: "John", lastName: "Smith"}]
        },
        {   name: "Sales",
            employees: [
                {firstName: "Paula", lastName: "Taylor"},
                {firstName: "Lisa", lastName: "Jones"}]
        }]
    };
     
    var tpl = "{{#depts}}

    {{name}}

    "
    +
              "
      {{#employees}}{{>employee}}{{/employees}}
    {{/depts}}"
    ;
    var partials = {employee: "
  • {{firstName}} {{lastName}}
  • "
    };
    var html = Mustache.to_html(tpl, data, partials);
    $('#sampleArea').html(html);
    Result:

    Engineering

    • Christophe Coenraets
    • John Smith

    Sales

    • Paula Taylor
    • Lisa Jones

    You can run all the examples here.


    4 comments:

    oakleyses said...

    louis vuitton handbags, oakley sunglasses, louboutin, longchamp outlet, nike shoes, louis vuitton outlet stores, chanel handbags, burberry outlet, prada outlet, jordan shoes, tiffany and co, michael kors outlet, tory burch outlet, louis vuitton outlet, longchamp handbags, nike free, true religion jeans, michael kors outlet, kate spade outlet, polo ralph lauren outlet, tiffany and co, prada handbags, polo ralph lauren outlet, michael kors outlet, michael kors outlet, longchamp handbags, oakley sunglasses, ray ban sunglasses, kate spade handbags, burberry outlet, louis vuitton outlet, louboutin outlet, louboutin, coach factory outlet, air max, air max, coach outlet, gucci outlet, christian louboutin shoes, michael kors outlet, coach purses, ray ban sunglasses, michael kors outlet, louis vuitton, coach outlet store online, true religion jeans, oakley sunglasses cheap

    oakleyses said...

    ralph lauren, lululemon, air max, hollister, north face, nike air max, polo lacoste, vanessa bruno, timberland, vans pas cher, louboutin, louis vuitton, oakley pas cher, air max pas cher, nike roshe run, air max, true religion outlet, barbour, sac longchamp, air force, hollister, sac louis vuitton, nike free, polo ralph lauren, nike trainers, louis vuitton uk, nike roshe, sac hermes, longchamp, michael kors, sac burberry, sac guess, mulberry, new balance pas cher, converse pas cher, sac louis vuitton, hogan outlet, nike tn, north face, true religion outlet, ray ban pas cher, michael kors, air jordan, nike blazer, nike free pas cher, michael kors pas cher, abercrombie and fitch, ray ban sunglasses

    oakleyses said...

    mac cosmetics, mont blanc, marc jacobs, canada goose outlet, nike huarache, vans shoes, soccer jerseys, hollister, giuseppe zanotti, beats by dre, abercrombie and fitch, longchamp, insanity workout, celine handbags, bottega veneta, ghd, nfl jerseys, north face outlet, chi flat iron, ugg boots, birkin bag, ugg australia, canada goose, herve leger, ugg pas cher, rolex watches, valentino shoes, canada goose uk, canada goose, ferragamo shoes, canada goose, ugg boots, uggs outlet, north face jackets, soccer shoes, asics running shoes, new balance shoes, p90x, lululemon outlet, canada goose jackets, mcm handbags, instyler, babyliss pro, ugg, wedding dresses, jimmy choo outlet, reebok outlet, nike roshe run

    oakleyses said...

    parajumpers, karen millen, air max, converse, pandora charms, moncler, louboutin, moncler, links of london, lancel, juicy couture outlet, oakley, hollister, pandora charms, supra shoes, thomas sabo, canada goose, gucci, wedding dresses, timberland boots, swarovski crystal, air max, coach outlet store online, moncler, ray ban, canada goose, moncler, ugg, louis vuitton, swarovski, hollister, montre homme, moncler, hollister clothing store, ralph lauren, rolex watches, moncler outlet, moncler, iphone 6 cases, baseball bats, juicy couture outlet, toms shoes, vans, pandora jewelry, ugg, converse shoes