Binding model data with TAL attributes
TAL is used to bind data from your application (a model) to your view. The following introduction shows - in most cases - a very limited example of the available functionality of each attribute. Each section carries links to more detailed documentation pages.
Inserting content
The two simplest TAL attributes to learn are tal:content
& tal:replace
;
they behave in a very similar manner.
<p>
Hello <strong tal:content="name">Joe Bloggs</strong>.
How are you on this fine <span tal:replace="dayOfWeek">Sunday</span>?
</p>
In each case, the attribute value is a TALES expression indicating the model value to be inserted. The above example might render as follows:
<p>
Hello <strong>Sarah Smith</strong>.
How are you on this fine Tuesday?
</p>
More information about content & repeat variables is available on the detailed documentation page.
Defining variables
In the previous example we made use of two imaginary variables (via TALES expressions).
These were name and dayOfWeek.
The tal:define
attribute is how we define/create those variables for real.
There are a small number of built-in variables provided by ZPT itself. Of those, here is the most important; it represents the model passed into the rendering process.
<div tal:define="customerName here/Customer/Name">
<p>Customer name: <span tal:content="customerName">Tony Fung</span>.</p>
</div>
The syntax of a define attribute is explored in depth in the detailed documentation. At its simplest the attribute value is the name of a variable you wish to define/create, followed by a space and then a TALES expression indicating the value for the new variable.
Conditional rendering
Another relatively simple TAL attribute is tal:condition
.
<div tal:define="hasOverdueBooks here/BooksOnLoan/HasAnyOverdue">
<p>Welcome to the library</p>
<p tal:condition="hasOverdueBooks" class="warning">
You have overdue books!
</p>
</div>
The attribute value is evaluated as a TALES expression The element with the condition attribute and its contents will be rendered if the expression value is "truth-like". If not then the element and its contents will be omitted.
More information, including what it means for a value to be "truth-like", is available on the documentation page for condition attributes.
Omitting start/end tags
Similar to the condition attribute is tal:omit-tag
.
<div tal:define="noRush here/DeadlineIsWeeksAway">
<em tal:omit-tag="noRush">
This content will be displayed with emphasis unless the deadline is weeks away,
as indicated by the <strong>noRush</strong> variable.
</em>
</div>
When using omit-tag, the contents of the element are always preserved and rendered. If the TALES expression is "truth-like" then the tag itself (including its end tag where applicable) is omitted from the rendering, but the contents are retained.
Further information, including what it means for a value to be "truth-like", is available on the omit-tag documentation page.
Repeating markup
A common requirement in rendering documents is to repeat a section of markup for items in a collection.
This is where tal:repeat
is used.
<!-- Source code for a sample data table representing a shopping list -->
<table tal:define="shoppingList here/ShoppingList">
<tr>
<th>Item</th>
<th>Quantity</th>
</tr>
<tr tal:repeat="item shoppingList">
<td tal:content="item/Name">Bagels</td>
<td tal:content="item/Quantity">4</td>
</tr>
</table>
<!-- Sample rendering of the above source code, for a model with 2 items -->
<table>
<tr>
<th>Item</th>
<th>Quantity</th>
</tr>
<tr>
<td>Bananas</td>
<td>2</td>
</tr>
<tr>
<td>Biscuits</td>
<td>2</td>
</tr>
</table>
The structure of the repeat attribute is similar to a TAL define attribute.
It begins with the name of a variable to declare and continues with
a TALES expression.
That expression should indicate a collection object (implementing IEnumerable
).
For each iteration of the collection, the declared variable exposes the current collection item.
This example demonstrates only some of the capabilities of the repeat attribute. There is much more to learn on its detailed documentation page.
Setting attributes
TAL may also be used to add/set or remove attributes to/from an element, using the
tal:attributes
attribute.
<div tal:define="reportUrl here/Article/ReportUrl">
If you have a concern, you may
<a href="article/0/report"
tal:attributes="href reportUrl">report this article</a>
to an administrator.
</div>
The syntax for the value for an attributes attribute is in two parts. The first part is the name of an attribute to change and the second is a TALES expression for the new attribute value.
There is more to learn about setting attributes in the detailed documentation.
Handling errors
The final TAL attribute handles errors encountered whilst rendering a document: tal:on-error
.
<!-- Source code for a login statement -->
<p tal:define="currentUser here/CurrentUser"
tal:on-error="string:You are not logged in.">
You are logged in as
<strong tal:content="currentUser/Username">jbloggs</strong>.
</p>
<!-- If the currentUser variable is null then this would render as shown: -->
<p>
You are not logged in.
</p>
If an error occurs when rendering an element (such as a TALES expression which cannot be evaluated) then the element and its parents are searched in order for an on-error attribute. The first such attribute found is treated as if it were a TAL content attribute. This avoids the entire rendering process terminating with an error.
The on-error attribute is explored in further detail on its documentation page.
Order of evaluation
The TAL rendering process visits every element in the source file in document order, fully processing all of the TAL attributes before moving onto the next. Within each element, TAL attributes are evaluated and processed in the following order:
- define
- condition
- repeat
- content or replace
- attributes
- omit-tag
The on-error attribute lives outside of this order. It is processed only if an error occurs and then immediately upon the occurrance of that error.
The order of evaluation is usually intuitive but be mindful of the opportunity for mistakes like this:
<!-- This won't work, define happens before repeat.
The "saying" variable won't exist when the define
attribute is evaluated -->
<ul>
<li tal:repeat="saying here/Sayings"
tal:define="formattedSaying string:As the saying goes - $saying">
<em tal:content="formattedSaying">As the saying goes - I told you so!</em>
</li>
</ul>
Additionally, a few of the above attributes can terminate the rendering process upon an element where it is pointless to continue. For example, a condition attribute may determine that the element and its children are not to be rendered. In this case further TAL attributes on the element will be ignored, as they cannot have any meaningful effect upon the result.