Pogonos is another Clojure(Script) implementation of the Mustache templating language.
Pogonos is still in beta. The public API provided in the pogonos.core
namespace is almost fixed while any other interfaces, including various
extension points (such as readers, outputs, AST nodes), are all subject
to change.
Add the following to your project's :dependencies
:
We will show you how to use Pogonos in this section, but if you're not too familiar with the Mustache language itself, you might want to read its documentation first.
The easiest way to use the library is to just call render-string
:
(require '[pogonos.core :as pg])
(pg/render-string "Hello, {{name}}!" {:name "Rich"})
;=> "Hello, Rich!"
render-string
takes two arguments; a string that represents a Mustache template,
and a map of the values passed to the template.
The keys of the map must be keywords.
The function, then, will render the template and return the resulting string. If you'd rather write out the rendering result to somewhere, instead of generating a string, you can use outputs to specify where to output the result. See Outputs for the details.
render-string
has look-alike cousins named render-file
and render-resource
.
The only difference between render-string
and those functions is that render-string
directly takes a template string as an argument whereas render-file
and
render-resource
load a template stored in a text file on the file system
or a resource file placed somewhere on the classpath.
Let's say you have a template file located at resources/sample.mustache
whose content looks like the following:
$ cat resources/sample.mustache
Hello, {{name}}!
Then, you can render the template using render-file
:
;; loads a template from a text file on the file system
(pg/render-file "resources/sample.mustache" {:name "Rich"})
Or if you have the template file on your classpath, you can also render it
with render-resource
(Here we assume the resources
directory is
included in the classpath):
;; loads a template from a resource file on the classpath
(pg/render-resource "sample.mustache" {:name "Rich"})
All the render functions mentioned above are more suitable for one-shot rendering. But if you want to render the same template with different contexts over and over again, it would be more efficient to prepare a parsed template prior to rendering.
To prepare a parsed template, use parse-string
(or parse-file
/ parse-resource
accordingly):
(def template (pg/parse-string "Hello, {{name}}!"))
template
;=> #pogonos.nodes.Root{:body ["Hello, " #pogonos.nodes.Variable{:keys (:name), :unescaped? false} "!"]}
And then, you can render the parsed template using the render
function:
(pg/render template {:name "Rich"})
;=> "Hello, Rich!"
(pg/render template {:name "Alex"})
;=> "Hello, Alex!"
At the time, Pogonos does NOT have an internal mechanism to implicitly cache parsing results for templates you've ever rendered, for better performance of rendering. So, if you're trying to use Pogonos where the rendering performance matters much, you may have to cache parsed templates on your own.
An output is the way to specify where to output the rendering result.
By default, Pogonos' render functions output the result as a string.
You can emulate this behavior by specifying (pogonos.output/to-string)
to them as the output like the following:
(require '[pogonos.output :as output])
(pg/render-string "Hello, {{name}}!" {:name "Clojure"}
{:output (output/to-string)})
;=> "Hello, Clojure!"
You can also write out the rendering result to a file or the stdout via output:
;; writes the rendering result to a file
(pg/render-string "Hello, {{name}}!" {:name "Clojure"}
{:output (output/to-file "hello.txt")})
;; writes the rendering result to the stdout
(pg/render-string "Hello, {{name}}!" {:name "Clojure"}
{:output (output/to-stdout)})
In general, it's more efficient to write out the rendering result directly to a file than to generate a resulting string, and then write it out to the file.
The Mustache spec provides a feature named partials. Partials can be used to include contents from other templates.
Let's say you have a partial resources/user.mustache
that looks like:
$ cat resources/user.mustache
<strong>{{name}}</strong>
You can render a template that has a partial in it using the render functions out of the box:
(pg/render-string "<h2>Users</h2>{{#users}}{{>user}}{{/users}}"
{:users [{:name "Rich"} {:name "Alex"}]})
;=> "<h2>Users</h2><strong>Rich</strong><strong>Alex</strong>"
By default, render-string
and render-resource
try to find
partials on the classpath, and render-file
on the file system.
To specify where to find partials explicitly, use the :partials
option:
(require '[pogonos.partials :as partials])
(pg/render-string "<h2>Users</h2>{{#users}}{{>user}}{{/users}}"
{:users [{:name "Rich"} {:name "Alex"}]}
{:partials (partials/file-partials "resources")})
(pg/render-string "<h2>Users</h2>{{#users}}{{>user}}{{/users}}"
{:users [{:name "Rich"} {:name "Alex"}]}
{:partials (partials/resource-partials)})
You can even specify a map to utilize inline partials:
(pg/render-string "<h2>Users</h2>{{#users}}{{>user}}{{/users}}"
{:users [{:name "Rich"} {:name "Alex"}]}
{:partials {:user "<strong>{{name}}</strong>"}}
Pogonos aims to provide user-friendly error messages for parse errors as one of its features, so that users can easily find where and why the error occurred.
For example, if you miss the closing delimiter of a Mustache tag, you'll see a detailed error message, like the following:
(pg/render-string "Hello, {{name" {:name "Clojure"})
;; Execution error (ExceptionInfo) at pogonos.error/error (error.cljc:52).
;; Missing closing delimiter "}}" (1:14):
;;
;; 1| Hello, {{name
;; ^^
You can suppress these somewhat "verbose" error messages if you want,
by specifying the option {:suppress-verbose-errors true}
:
(pg/render-string "Hello, {{name" {:name "Clojure"}
{:suppress-verbose-errors true})
;; Execution error (ExceptionInfo) at pogonos.error/error (error.cljc:52).
;; Missing closing delimiter "}}" (1:14)
Even while disabling verbose error messages, you can get them back by calling
perr
explicitly:
(pg/perr *e)
;; Missing closing delimiter "}}" (1:14):
;;
;; 1| Hello, {{name
;; ^^
Copyright © 2020 Shogo Ohta
This program and the accompanying materials are made available under the terms of the Eclipse Public License 2.0 which is available at http://www.eclipse.org/legal/epl-2.0.
This Source Code may also be made available under the following Secondary Licenses when the conditions for such availability set forth in the Eclipse Public License, v. 2.0 are satisfied: GNU General Public License as published by the Free Software Foundation, either version 2 of the License, or (at your option) any later version, with the GNU Classpath Exception which is available at https://www.gnu.org/software/classpath/license.html.
Can you improve this documentation? These fine people already did:
Shogo Ohta & Ohta ShogoEdit on GitHub
cljdoc is a website building & hosting documentation for Clojure/Script libraries
× close