Introduction to mustache

Summary

Is it moustache or mustache? Moustache, mustache, and mustachio all describe hair grown on the upper lip. Mustache describes a mustache in communities where American English is spoken. Moustache is used in British English communities. Mustachio can optionally be used to describe an unusually large mustache or moustache.


You can remember to use moustache in British English by keeping in mind that moustache and London are both spelled with an O. Otherwise, this article can serve as a helpful reminder if you are having trouble choosing moustache, mustache, or mustachio.

To summarize,

  • Moustache is the British English spelling of the word.
  • Mustache in the American English spelling of the word.

Contents

Mustache Sections and Iterations

Let’s now have a look at how to list the todos. For iterating over a list data, we make use of Mustache sections.

A section is a block of code which is repeated one or more times depending on the value of the key in the current context.

It looks something like:

A section begins with a pound (#) and ends with a slash (/), where each of the signs is followed by the key whose value is used as the basis for rendering the section.

Following are the scenarios that can occur depending on the value of the key:

5.1. Section With Non-Empty List or Non-False Value

Let’s create a template todo-section.mustache which uses a section:

Let’s look at this template in action:

Let’s create another template todos.mustache for listing the todos:

And create a listing of todos using it:

Defining Mustache Templates

There are various methods for defining mustache templates in your application. These methods are similar to including CSS using inline styles, inline stylesheets, and external stylesheets. The example we discussed earlier can be considered as an inline method since we are passing the template directly to the function. This method prevents the possibility of reusable templates. Let’s see how we can define templates as inline script templates as opposed to directly passing to the function.

Templates as Inline Scripts

We can define template data inside of a tag and include it in the HTML document. To prevent the browser from executing the template code, we must change the MIME type to something other than . Some common MIME types are , , and . The following example is a simple template using this method.

You can include as many templates in a document as you wish with different IDs. When you want to use the template, get the HTML inside the script tag using , and pass it as a template. Our first example will change to the following code.

As you can see, templates are stored separately and used dynamically when required. This method increases the possibility of reusing templates. However, using inline scripts limits the templates’ scope to a single page. If you have multiple pages, you have to define your templates again. So, including templates in an external file will be the ideal solution – just like with CSS.

Templates as External HTML Snippets

In this technique we are going to use jQuery to implement templating. jQuery provides a function called , which can be used to fetch part of an external document. We are going to use this method to load templates dynamically from our external templates files. The function executes scripts instead of returning them, so we cannot create templates inside of script tags as we did in the previous method. The following example shows the external template files we are going to use.

We have used elements for templates instead of scripts to keep it compatible with jQuery’s function. Here, we have three different templates with three different IDs. Now, let’s move on to using these templates in your pages.

jQuery inserts the returned document into an HTML element instead of assigning it to a variable. So, we need a dummy container to keep the templates. I have used the container which is hidden by default. The example above retrieves , and loads it. Then, we can get the template from the dummy container and pass it to mustache for rendering. This is how the external method works. We can also get the data from a server using an AJAX request.

Sections

In the main example, the template included:

Tags beginning with and closed with create sections. The part between them is used only if the variable is defined.

If the section name refers to a function, that function will be passed the unevaluated string within the section, as expected by the Mustache specification. (If the tag «|» is used, the section value will be rendered first, an enhancement to the specification.)

Inverted

Related, if the tag begins with and ends with the text between these tags is included only if the variable is not defined or is .

Iteration

If the section variable, , binds to an iterable collection, then the text in the section is repeated for each item in the collection with the view used for the context of the template given by the item.

This is useful for collections of named objects, such as DataFrames (where the collection is comprised of rows) or arrays of dictionaries. For objects the rows are iterated over.

For data frames, the variable names are specified as symbols or strings. Here is a template for making a web page:

tpl = mt"""
<html>
<head>
<title>{{:TITLE}}</title>
</head>
<body>
<table>
<tr><th>name</th><th>summary</th></tr>
{{#:D}}
<tr><td>{{:names}}</td><td>{{:summs}}</td></tr>
{{/:D}}
</body>
</html>
"""

This can be used to generate a web page for -like values:

_names = String[]
_summaries = String[]
for s in sort(map(string, names(Main)))
    v = Symbol(s)
    if isdefined(Main,v)
        push!(_names, s)
        push!(_summaries, summary(eval(v)))
    end
end

using DataFrames
d = DataFrame(names=_names, summs=_summaries)

out = render(tpl, TITLE="A quick table", D=d)
print(out)

This can be compared to using an array of s, convenient if you have data by the row:

A = 
tpl = mt"{{#:A}}Pronounce a as {{a}} and b as {{b}}. {{/:A}}"
render(tpl, A=A) |> print

yielding


The same approach can be made to make a LaTeX table from a data frame:

function df_to_table(df, label="label", caption="caption")
    fmt = repeat("c", size(df,2))
    header = join(string.(names(df)), " & ")
    row = join(, " & ")

tpl="""
\\begin{table}
  \\centering
  \\begin{tabular}{$fmt}
  $header\\\\
{{#:DF}}    $row\\\\
{{/:DF}}  \\end{tabular}
  \\caption{$caption}
  \\label{tab:$label}
\\end{table}
"""

    Mustache.render(tpl, DF=df)
end

(A string is used above — and not a macro — so that string interpolation can happen.)

Iterating over vectors

Though it isn’t part of the Mustache specification, when iterating over an unnamed vector, Mustache.jl uses to refer to the item:

tpl = "{{#:vec}}{{.}} {{/:vec}}"
render(tpl, vec = )  # "A1 B2 C3 "

Note the extra space after .

There is also limited support for indexing with the iteration of a vector that allows one to treat the last element differently. The syntax refers to the value . (There is no support for the usual arithmetic on indices.)

To print commas one can use this pattern:

tpl = "{{#:vec}}{{.}}{{^.}}, {{/.}}{{/:vec}}"
render(tpl, vec = )  # "A1, B2, C3"

To put the first value in bold, but no others, say:

tpl = """
{{#:vec}}
{{#.}}<bold>{{.}}</bold>{{/.}}
{{^.}}{{.}}{{/.}}
{{/:vec}}
"""
render(tpl, vec = )  # basically "<bold>A1</bold>B2 C3"

Partials

Partials are used to include partial templates into a template.

Partials begin with a greater than sign, like . In this example, the file is opened and inserted into the template, then populated. A full path may be specified.

They also inherit the calling context.

In this way you may want to think of partials as includes, imports, template expansion, nested templates, or subtemplates, even though those aren’t literally the case here.

The partial specified by is not parsed, rather included as is into the file. This can be faster.

Features

Hogan is fast—try it on your workload.

Hogan has separate scanning, parsing and code generation phases. This way it’s possible to add new features without touching the scanner at all, and many different code generation techniques can be tried without changing the parser.

Hogan exposes scan and parse methods. These can be useful for pre-processing templates on the server.

var text = "{{^check}}{{#i18n}}No{{/i18n}}{{/check}}";
text +=  "{{#check}}{{#i18n}}Yes{{/i18n}}{{/check}}";
var tree = Hogan.parse(Hogan.scan(text));

// outputs "# check"
console.log(tree.tag + " " + tree.name);

// outputs "Yes"
console.log(tree1.nodes.nodes);

It’s also possible to use HoganTemplate objects without the Hogan compiler present. That means you can pre-compile your templates on the server, and avoid shipping the compiler. However, the optional lambda features from the Mustache spec require the compiler and the original template source to be present.

Hogan also supports template inheritance, and maintains compatibility with other implementations like mustache.java, mustache.php, and GRMustache

Conclusion

Template engines and frameworks are important in managing complex systems with dynamically changing presentation views. Mustache.js is one of the best choices for managing templates on the client side. We started this tutorial by explaining why templates are important. Then, we moved onto various techniques of using mustache templates. Now you will be able to choose the method of implementing mustache templates in your projects.

We have completed exploring various techniques for using mustache templates, but mustache also comes with tags such as variables, sections, functions and partials, which are used to manage complex templates. Discussing the syntax of each tag is beyond the scope of this tutorial. You can find a comprehensive guide to mustache tags on the mustache GitHub page.

Feel free to share your previous experiences in working with mustache.js!

Lambdas

JMustache implements lambdas by passing you a instance which you can use to execute the fragment of the template that was passed to the lambda. You can decorate the results of the fragment execution, as shown in the standard Mustache documentation on lambdas:

String tmpl = "{{#bold}}{{name}} is awesome.{{/bold}}";
Mustache.compiler().compile(tmpl).execute(new Object() {
   String name = "Willy";
   Mustache.Lambda bold = new Mustache.Lambda() {
        public void execute (Template.Fragment frag, Writer out) throws IOException {
            out.write("<b>");
            frag.execute(out);
            out.write("</b>");
        }
    };
});
// result:
<b>Willy is awesome.<b>

You can also obtain the results of the fragment execution to do things like internationalization or caching:

Object ctx = new Object() {
    Mustache.Lambda i18n = new Mustache.Lambda() {
         public void execute (Template.Fragment frag, Writer out) throws IOException {
             String key = frag.execute();
             String text = // look up key in i18n system
             out.write(text);
         }
    };
};
// template might look something like:
<h2>{{#i18n}}title{{i18n}<h2>
{{#i18n}}welcome_msg{{i18n}}

Разработка HTML + Mustache шаблонов

Существует несколько способов встроить mustache шаблоны в ваше веб приложение. Эти методы схожи с подключением CSS стилей. То есть, можно прописывать строкой кода, блоком, или подключать внешний файл. Пример, который рассматривали раньше, является строковым подключением шаблона. Рассмотрим, как можно использовать шаблоны в качестве строковых скриптов.

Подключение шаблонов строковым методом

Мы можем определить шаблон внутри тега <script>, который включить в HTML структуру кода. Чтобы предотвратить обработку кода шаблона, необходимо изменить MIME тип text/javascript, на что-то другое. Можно использовать следующие MIME типы: text/html, text/template, text/mustache. Следующий пример, показывает как это реализовать:

<script id="sample_template" type="text/html">
<h1>{{name}}</h1>
</script>

Вы можете встраивать множество шаблонов с разными ID в тело HTML документа. Когда потребуется его использовать, достаточно вызвать innerHTML, и передать в функцию render() как шаблон. Вот так:

<script type='text/javascript'>
  var template = document.getElementById('sample_template').innerHTML;
  var output = Mustache.render(template, view);
  document.getElementById('person').innerHTML = output;
</script>

Как видно, шаблоны хранятся отдельно и используются динамически, только когда это нужно. Такой подход увеличивает возможности повторного использования шаблонов. Хотя, использование строковых скриптов ограничивает видимость шаблонов в рамках одной страницы. Если у вас несколько страниц, надо определять шаблоны снова. Поэтому, подключение шаблонов как внешних файлов будет идеальным решением – как в случае с CSS.

Шаблоны как внешние HTML сниппеты

В этом случае, мы будем использовать jQuery для подключения шаблонов. jQuery предоставляет функцию load(), которая позволяет подключать внешние куски кода документа. Load() функция не выполняет скрипты, потому нам не надо заключать шаблон в тег <script>, как мы делали в предыдущем варианте. Следующий код показывает как выглядит внешний подключаемый шаблон:

<div id="template1" >
<h1>{{name}}</h1>
</div>
<div id="template2" >
<div>{{name}}</div>
</div>
<div id="template3" >
<p><span>{{name}}</span></p>
</div>

Вместо тега <script>, мы используем <div> блок, чтобы отделить один шаблон от другого. Мы имеем три разных шаблона с разными ID блоков. Теперь перейдем к их использованию в теле документа:

<!doctype html>
<html lang="en">
  <head>
    <title>Mustache.js External Method</title>
    <script type="text/javascript" src="jquery.js" ></script>
    <script type="text/javascript" src="mustache.js" ></script>
    <script>
      $(document).ready(function(){
        var view = {
          name : "Joe",
          occupation : "Web Developer"
        };
        $("#templates").load("template.html #template1",function(){
          var template = document.getElementById('template1').innerHTML;
          var output = Mustache.render(template, view);
          $("#person").html(output);
        });
      });
    </script>
  </head>
  <body>
    <p id="person"></p>
    <div id="templates" style="display: none;"></div>
  </body>
</html>

jQuery вставляет HTML код в тело документа, не в переменную! Поэтому нам надо создать отдельный блок для шаблонов. В примере использован templates, который скрыт по умолчанию. В коде выше, мы получаем template1 и загружаем его. Теперь можем получить шаблон из блока документа и передать на обработку в mustache. Вот как работает этот способ. Так же можно получать данные из сервера используя AJAX запросы.

TAG TYPES

Tags are indicated by the double mustaches. is a tag, as is . In both examples, we’d refer to as the key or tag key. Let’s talk about the different types of tags.

Variables

The most basic tag type is the variable. A tag in a basic template will try to find the key in the current context. If there is no key, the parent contexts will be checked recursively. If the top context is reached and the key is still not found, nothing will be rendered.

All variables are HTML escaped by default. If you want to return unescaped HTML, use the triple mustache: .

You can also use to unescape a variable: . This may be useful when changing delimiters (see «Set Delimiter» below).

By default a variable «miss» returns an empty string. This can usually be configured in your Mustache library. The Ruby version of Mustache supports raising an exception in this situation, for instance.

Template:

Hash:

Output:

Sections

Sections render blocks of text one or more times, depending on the value of the key in the current context.

A section begins with a pound and ends with a slash. That is, begins a «person» section while ends it.

The behavior of the section is determined by the value of the key.

False Values or Empty Lists

If the key exists and has a value of false or an empty list, the HTML between the pound and slash will not be displayed.

Template:

Hash:

Output:

Non-Empty Lists

If the key exists and has a non-false value, the HTML between the pound and slash will be rendered and displayed one or more times.

When the value is a non-empty list, the text in the block will be displayed once for each item in the list. The context of the block will be set to the current item for each iteration. In this way we can loop over collections.

Template:

Hash:


Output:

Lambdas

When the value is a callable object, such as a function or lambda, the object will be invoked and passed the block of text. The text passed is the literal block, unrendered. will not have been expanded — the lambda should do that on its own. In this way you can implement filters or caching.

Template:

Hash:

Output:

Non-False Values

When the value is non-false but not a list, it will be used as the context for a single rendering of the block.

Template:

Hash:

Output:

Inverted Sections

An inverted section begins with a caret (hat) and ends with a slash. That is begins a «person» inverted section while ends it.

While sections can be used to render text one or more times based on the value of the key, inverted sections may render text once based on the inverse value of the key. That is, they will be rendered if the key doesn’t exist, is false, or is an empty list.

Template:

Hash:

Output:

Comments

Comments begin with a bang and are ignored. The following template:

Will render as follows:

Comments may contain newlines.

Partials

Partials begin with a greater than sign, like .

Partials are rendered at runtime (as opposed to compile time), so recursive partials are possible. Just avoid infinite loops.

They also inherit the calling context. Whereas in an (http://en.wikipedia.org/wiki/ERuby) file you may have this:

Mustache requires only this:

Why? Because the file will inherit the and methods from the calling context.

In this way you may want to think of partials as includes, imports, template expansion, nested templates, or subtemplates, even though those aren’t literally the case here.

For example, this template and partial:

Can be thought of as a single, expanded template:

Set Delimiter

Set Delimiter tags start with an equal sign and change the tag delimiters from and to custom strings.

Consider the following contrived example:

Here we have a list with three items. The first item uses the default tag style, the second uses erb style as defined by the Set Delimiter tag, and the third returns to the default style after yet another Set Delimiter declaration.

According to ctemplates, this «is useful for languages like TeX, where double-braces may occur in the text and are awkward to use for markup.»

Custom delimiters may not contain whitespace or the equals sign.

Gallery

Mustache Waxer’s statistics

Mustache Waxer’s card

Mustache Waxer unlocked

Mustache Waxer’s grayed out card

Mustache Waxer’s card image

HD Mustache Waxer

Mustache Waxer’s textures

Mustache Waxer activating his ability

Mustache Waxer attacking

Mustache Waxer destroyed

Mustache Waxer shrunken by Shrinking Violet

Mustache Waxer frozen (note his hand)


Rock Wall being used on Mustache Waxer

Weed Whack being used on Mustache Waxer

Iceberg Lettuce being used on Mustache Waxer

Mustache Waxer with the Deadly trait

Mustache Waxer with the trait due to Parasol Zombie’s ability

Mustache Waxer with 2/3 due to Pecanolith’s ability

Precision Blast being used on Mustache Waxer.

Add a photo to this gallery

Helpers

What about global helpers? Maybe you have a nifty function you want to use in all your views? No problem.

This is just Ruby, after all.

module ViewHelpers
  def gravatar
    gravatar_id = Digest::MD5.hexdigest(self:email.to_s.strip.downcase)
    gravatar_for_id(gravatar_id)
  end

  def gravatar_for_id(gid, size = 30)
    "#{gravatar_host}/avatar/#{gid}?s=#{size}"
  end

  def gravatar_host
    @ssl ? 'https://secure.gravatar.com' : 'http://www.gravatar.com'
  end
end

Then just include it:

class Simple < Mustache
  include ViewHelpers

  def name
    "Chris"
  end

  def value
    10_000
  end

  def taxed_value
    value * 0.6
  end

  def in_ca
    true
  end

  def users
    User.all
  end
end

Great, but what about that ivar in ? There are many ways we can go about setting it.

Here’s an example which illustrates a key feature of Mustache: you are free to use the method just as you would in any normal class.

class Simple < Mustache
  include ViewHelpers

  def initialize(ssl = false)
    @ssl = ssl
  end
end

Now:

Simple.new(request.ssl?).render

Finally, our template might look like this:

Testing

$ git submodule init$ git submodule update

Install dependencies.

$ npm install

Then run the tests.

$ npm test

The test suite consists of both unit and integration tests. If a template isn’t rendering correctly for you, you can make a test for it by doing the following:

  1. Create a template file named in the directory. Replace with the name of your test.
  2. Create a corresponding view file named in the same directory. This file should contain a JavaScript object literal enclosed in parentheses. See any of the other view files for an example.
  3. Create a file with the expected output in in the same directory.

Then, you can run the test with:

$ TEST=mytest npm run test-render

Browser tests are not included in as they run for too long, although they are ran automatically on Travis when merged into master. Run browser tests locally in any browser:

$ npm run test-browser-local

then point your browser to

Сюжет

Если честно, то игра совершенно не длинная, но в неё хочется переигрывать снова и снова. У вас очень важная миссия, вы любым способом должны уничтожить армию противников, которая, в начале, может показаться непобедимой. Поначалу у вас будет один единственный солдат с элементарным оружием, но после того, как он убьет одного из соперника, вы получите возможность приобрести на заработанные деньги нового солдата, или даже робота, после чего вы можете снова вступить в бой. Однако уже будет одно отличие от первого боя, теперь ваш солдат будет полностью повторять ваши действия. После каждой смерти, вы можете покупать себе новых воинов. В итоге у вас соберется большая армия солдат, которыми вам предстоит, умело управлять. Ваша задача – победить противников, и добраться до самой главной башни, чтобы впоследствии уничтожить ее. Быстро ли вы с этим справитесь? Или вы сможете одержать победу только с одним солдатом? Попробуйте скачать Mustache Armies через торрент совершенно бесплатно на нашем замечательном игровом ресурсе, и окунитесь в мир путешествий. Мы уверены, игра вам, несомненно, понравится!

Why We Need Template Systems

Most developers that are not aware of template systems create new chunks of HTML code and dynamically insert them into the DOM using JavaScript. A common way of doing this is to specify the HTML elements in a string and then set the property or call the jQuery method. An example of this technique is shown below.

Another method for building the DOM is to create elements and append them individually, as shown below.

Both the methods above can be used effectively to add elements dynamically into your document. Consider a situation where we have a very well designed bullet list which needs to be used across three different types of pages in our site. Using these techniques, we would have to repeat the HTML code the list in three different locations. This is generally considered to be bad coding practice.

In such scenarios we can use predefined templates in different locations without repeating the code. Mustache.js is a very popular template engine using JavaScript. Since mustache provides both server side and client side templates for numerous languages, we don’t have to worry about choosing separate template engines.

Layouts

The way the layouts work with the other template languages in Scalate is you define attributes inside the templates which are then passed into the layout template as template attributes. However Mustache has no ‘set attribute’ syntax since its a ‘no logic in the template’ style.

The Mustache approach is inside a layout template we can use the {{#html}} section to navigate the HTML of the template output.

For example this template sample.mustache we could apply this layout mylayout.mustache to generate

Inside the {{#html}} section we can then pull out child elements by name. So inside the {{#head}} section you can refer to {{title}} and you’ll get the entire <title> element (attributes and all).

If you want just the children an element, create a section for it and use {{_}} (e.g. the way we exclude the <body> element in the layout but just use all the children). Names starting with @ refer to attributes. (This is using the ** method on NodeSeq underneath).

History and principles

Mustache-1 was inspired by ctemplate and et, and started as a GitHub distribution at the end of 2009. A first version of the template engine was implemented with Ruby, running YAML template texts. The (preserved) main principles were:

  • «logic-less»: no explicit control flow statements, all control driven by data.
  • strong «separating logic from presentation»: it is impossible to embed application logic in the Mustache templates.

The input data can be a class, so input data can be characterized as an MVC-view. The Mustache template does nothing but reference methods in the (input data) view. All the logic, decisions, and code is contained in this view, and all the markup (ex. output XML) is contained in the template. In an MVP context: input data is from MVP-presenter, and the Mustache template is the MVP-view.


С этим читают