9 QWeb is the primary templating_ engine used by Odoo\ [#othertemplates]_. It
10 is an XML templating engine\ [#genshif]_ and used mostly to generate HTML_
13 Template directives are specified as XML attributes prefixed with ``t-``,
14 for instance ``t-if`` for :ref:`reference/qweb/conditionals`, with elements
15 and other attributes being rendered directly.
17 To avoid element rendering, a placeholder element ``<t>`` is also available,
18 which executes its directive but doesn't generate any output in and of
29 if ``condition`` is true, but::
31 <div t-if="condition">
41 .. _reference/qweb/output:
46 QWeb has a primary output directive which automatically HTML-escape its
47 content limiting XSS_ risks when displaying user-provided content: ``esc``.
49 ``esc`` takes an expression, evaluates it and prints the content::
51 <p><t t-esc="value"/></p>
53 rendered with the value ``value`` set to ``42`` yields::
57 There is one other output directive ``raw`` which behaves the same as
58 respectively ``esc`` but *does not HTML-escape its output*. It can be useful
59 to display separately constructed markup (e.g. from functions) or already
60 sanitized user-provided markup.
62 .. _reference/qweb/conditionals:
67 QWeb has a conditional directive ``if``, which evaluates an expression given
76 The element is rendered if the condition is true::
82 but if the condition is false it is removed from the result::
87 The conditional rendering applies to the bearer of the directive, which does
88 not have to be ``<t>``::
91 <p t-if="condition">ok</p>
94 will give the same results as the previous example.
96 .. _reference/qweb/loops:
101 QWeb has an iteration directive ``foreach`` which take an expression returning
102 the collection to iterate on, and a second parameter ``t-as`` providing the
103 name to use for the "current item" of the iteration::
105 <t t-foreach="[1, 2, 3]" t-as="i">
106 <p><t t-esc="i"/></p>
109 will be rendered as::
115 Like conditions, ``foreach`` applies to the element bearing the directive's
120 <p t-foreach="[1, 2, 3]" t-as="i">
124 is equivalent to the previous example.
126 ``foreach`` can iterate on an array (the current item will be the current
127 value), a mapping (the current item will be the current key) or an integer
128 (equivalent to iterating on an array between 0 inclusive and the provided
131 In addition to the name passed via ``t-as``, ``foreach`` provides a few other
132 variables for various data points:
134 .. warning:: ``$as`` will be replaced by the name passed to ``t-as``
137 the object being iterated over
139 the current iteration value, identical to ``$as`` for lists and integers,
140 but for mappings it provides the value (where ``$as`` provides the key)
142 the current iteration index (the first item of the iteration has index 0)
144 the size of the collection if it is available
146 whether the current item is the first of the iteration (equivalent to
147 :samp:`{$as}_index == 0`)
149 whether the current item is the last of the iteration (equivalent to
150 :samp:`{$as}_index + 1 == {$as}_size`), requires the iteratee's size be
153 either ``"even"`` or ``"odd"``, the parity of the current iteration round
155 a boolean flag indicating that the current iteration round is on an even
158 a boolean flag indicating that the current iteration round is on an odd
161 .. _reference/qweb/attributes:
166 QWeb can compute attributes on-the-fly and set the result of the computation
167 on the output node. This is done via the ``t-att`` (attribute) directive which
168 exists in 3 different forms:
170 :samp:`t-att-{$name}`
171 an attribute called ``$name`` is created, the attribute value is evaluated
172 and the result is set as the attribute's value::
176 will be rendered as::
179 :samp:`t-attf-{$name}`
180 same as previous, but the parameter is a :term:`format string`
181 instead of just an expression, often useful to mix literal and non-literal
182 string (e.g. classes)::
184 <t t-foreach="[1, 2, 3]" t-as="item">
185 <li t-attf-class="row {{ item_parity }}"><t t-esc="item"/></li>
188 will be rendered as::
190 <li class="row even">1</li>
191 <li class="row odd">2</li>
192 <li class="row even">3</li>
193 :samp:`t-att=mapping`
194 if the parameter is a mapping, each (key, value) pair generates a new
195 attribute and its value::
197 <div t-att="{'a': 1, 'b': 2}"/>
199 will be rendered as::
201 <div a="1" b="2"></div>
203 if the parameter is a pair (tuple or array of 2 element), the first
204 item of the pair is the name of the attribute and the second item is the
207 <div t-att="['a', 'b']"/>
209 will be rendered as::
216 QWeb allows creating variables from within the template, to memoize a
217 computation (to use it multiple times), give a piece of data a clearer name,
220 This is done via the ``set`` directive, which takes the name of the variable
221 to create. The value to set can be provided in two ways:
223 * a ``t-value`` attribute containing an expression, and the result of its
224 evaluation will be set::
226 <t t-set="foo" t-value="2 + 1"/>
230 * if there is no ``t-value`` attribute, the node's body is rendered and set
231 as the variable's value::
238 will generate ``<li>ok</li>`` (the content is escaped as we
239 used the ``esc`` directive)
241 .. note:: using the result of this operation is a significant use-case for
242 the ``raw`` directive.
244 calling sub-templates
245 =====================
247 QWeb templates can be used for top-level rendering, but they can also be used
248 from within another template (to avoid duplication or give names to parts of
249 templates) using the ``t-call`` directive::
251 <t t-call="other-template"/>
253 This calls the named template with the execution context of the parent, if
254 ``other_template`` is defined as::
256 <p><t t-value="var"/></p>
258 the call above will be rendered as ``<p/>`` (no content), but::
260 <t t-set="var" t-value="1"/>
261 <t t-call="other-template"/>
263 will be rendered as ``<p>1</p>``.
265 However this has the problem of being visible from outside the ``t-call``.
266 Alternatively, content set in the body of the ``call`` directive will be
267 evaluated *before* calling the sub-template, and can alter a local context::
269 <t t-call="other-template">
270 <t t-set="var" t-value="1"/>
272 <!-- "var" does not exist here -->
274 The body of the ``call`` directive can be arbitrarily complex (not just
275 ``set`` directives), and its rendered form will be available within the called
276 template as a magical ``0`` variable::
279 This template was called with content:
285 <t t-call="other-template">
292 This template was called with content:
305 .. todo:: have fme write these up because I've no idea how they work
307 "smart records" fields formatting
308 '''''''''''''''''''''''''''''''''
310 The ``t-field`` directive can only be used when performing field access
311 (``a.b``) on a "smart" record (result of the ``browse`` method). It is able
312 to automatically format based on field type, and is integrated in the
313 website's rich text edition.
315 ``t-field-options`` can be used to customize fields, the most common option
316 is ``widget``, other options are field- or widget-dependent.
324 Most Python-side uses of QWeb are in controllers (and during HTTP requests),
325 in which case templates stored in the database (as
326 :ref:`views <reference/views/qweb>`) can be trivially rendered by calling
327 :meth:`openerp.http.HttpRequest.render`:
329 .. code-block:: python
331 response = http.request.render('my-template', {
335 This automatically creates a :class:`~openerp.http.Response` object which can
336 be returned from the controller (or further customized to suit).
341 At a deeper level than the previous helper is the ``render`` method on
344 .. py:method:: render(cr, uid, id[, values][, engine='ir.qweb][, context])
346 Renders a QWeb view/template by database id or :term:`external id`.
347 Templates are automatically loaded from ``ir.ui.view`` records.
349 Sets up a number of default values in the rendering context:
352 the current :class:`~openerp.http.WebRequest` object, if any
354 whether the current request (if any) is in ``debug`` mode
355 :func:`quote_plus <werkzeug.urls.url_quote_plus>`
356 url-encoding utility function
358 the corresponding standard library module
360 the corresponding standard library module
362 the corresponding standard library module
363 `relativedelta <https://labix.org/python-dateutil#head-ba5ffd4df8111d1b83fc194b97ebecf837add454>`_
366 the ``keep_query`` helper function
368 :param values: context values to pass to QWeb for rendering
369 :param str engine: name of the Odoo model to use for rendering, can be
370 used to expand or customize QWeb locally (by creating
371 a "new" qweb based on ``ir.qweb`` with alterations)
373 .. _reference/qweb/javascript:
378 It is also possible to use the ``ir.qweb`` model directly (and extend it, and
381 .. automodule:: openerp.addons.base.ir.ir_qweb
382 :members: QWeb, QWebContext, FieldConverter, QwebWidget
393 The ``t-name`` directive can only be placed at the top-level of a template
394 file (direct children to the document root)::
397 <t t-name="template-name">
398 <!-- template code -->
402 It takes no other parameter, but can be used with a ``<t>`` element or any
403 other. With a ``<t>`` element, the ``<t>`` should have a single child.
405 The template name is an arbitrary string, although when multiple templates
406 are related (e.g. called sub-templates) it is customary to use dot-separated
407 names to indicate hierarchical relationships.
412 Template inheritance is used to alter existing templates in-place, e.g. to
413 add information to templates created by an other modules.
415 Template inheritance is performed via the ``t-extend`` directive which takes
416 the name of the template to alter as parameter.
418 The alteration is then performed with any number of ``t-jquery``
421 <t t-extends="base.template">
422 <t t-jquery="ul" t-operation="append">
427 The ``t-jquery`` directives takes a `CSS selector`_. This selector is used
428 on the extended template to select *context nodes* to which the specified
429 ``t-operation`` is applied:
432 the node's body is appended at the end of the context node (after the
433 context node's last child)
435 the node's body is prepended to the context node (inserted before the
436 context node's first child)
438 the node's body is inserted right before the context node
440 the node's body is inserted right after the context node
442 the node's body replaces the context node's children
444 the node's body is used to replace the context node itself
446 if no ``t-operation`` is specified, the template body is interpreted as
447 javascript code and executed with the context node as ``this``
449 .. warning:: while much more powerful than other operations, this mode is
450 also much harder to debug and maintain, it is recommended to
456 The javascript QWeb implementation provides a few debugging hooks:
459 takes an expression parameter, evaluates the expression during rendering
460 and logs its result with ``console.log``
462 triggers a debugger breakpoint during template rendering
464 the node's body is javascript code executed during template rendering.
465 Takes a ``context`` parameter, which is the name under which the rendering
466 context will be available in the ``t-js``'s body
471 .. js:attribute:: openerp.qweb
473 An instance of :js:class:`QWeb2.Engine` with all module-defined template
474 files loaded, and references to standard helper objects ``_``
475 (underscore), ``_t`` (translation function) and JSON_.
477 :js:func:`openerp.qweb.render <QWeb2.Engine.render>` can be used to
478 easily render basic module templates
483 .. js:class:: QWeb2.Engine
485 The QWeb "renderer", handles most of QWeb's logic (loading,
486 parsing, compiling and rendering templates).
488 OpenERP Web instantiates one for the user, and sets it to
489 ``instance.web.qweb``. It also loads all the template files of the
490 various modules into that QWeb instance.
492 A :js:class:`QWeb2.Engine` also serves as a "template namespace".
494 .. js:function:: QWeb2.Engine.render(template[, context])
496 Renders a previously loaded template to a String, using
497 ``context`` (if provided) to find the variables accessed
498 during template rendering (e.g. strings to display).
500 :param String template: the name of the template to render
501 :param Object context: the basic namespace to use for template
505 The engine exposes an other method which may be useful in some
506 cases (e.g. if you need a separate template namespace with, in
507 OpenERP Web, Kanban views get their own :js:class:`QWeb2.Engine`
508 instance so their templates don't collide with more general
511 .. js:function:: QWeb2.Engine.add_template(templates)
513 Loads a template file (a collection of templates) in the QWeb
514 instance. The templates can be specified as:
517 QWeb will attempt to parse it to an XML document then load
521 QWeb will attempt to download the URL content, then load
522 the resulting XML string.
524 A ``Document`` or ``Node``
525 QWeb will traverse the first level of the document (the
526 child nodes of the provided root) and load any named
527 template or template override.
529 :type templates: String | Document | Node
531 A :js:class:`QWeb2.Engine` also exposes various attributes for
532 behavior customization:
534 .. js:attribute:: QWeb2.Engine.prefix
536 Prefix used to recognize directives during parsing. A string. By
539 .. js:attribute:: QWeb2.Engine.debug
541 Boolean flag putting the engine in "debug mode". Normally,
542 QWeb intercepts any error raised during template execution. In
543 debug mode, it leaves all exceptions go through without
546 .. js:attribute:: QWeb2.Engine.jQuery
548 The jQuery instance used during template inheritance processing.
549 Defaults to ``window.jQuery``.
551 .. js:attribute:: QWeb2.Engine.preprocess_node
553 A ``Function``. If present, called before compiling each DOM
554 node to template code. In OpenERP Web, this is used to
555 automatically translate text content and some attributes in
556 templates. Defaults to ``null``.
558 .. [#genshif] it is similar in that to Genshi_, although it does not use (and
559 has no support for) `XML namespaces`_
561 .. [#othertemplates] although it uses a few others, either for historical
562 reasons or because they remain better fits for the
563 use case. Odoo 8.0 still depends on Jinja_ and Mako_.
566 http://en.wikipedia.org/wiki/Template_processor
568 .. _Jinja: http://jinja.pocoo.org
569 .. _Mako: http://www.makotemplates.org
570 .. _Genshi: http://genshi.edgewall.org
571 .. _XML namespaces: http://en.wikipedia.org/wiki/XML_namespace
572 .. _HTML: http://en.wikipedia.org/wiki/HTML
573 .. _XSS: http://en.wikipedia.org/wiki/Cross-site_scripting
574 .. _JSON: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/JSON
575 .. _CSS selector: http://api.jquery.com/category/selectors/