Conditionals: @if, @else, @elseif, @endif
Show one block when a condition is true, optionally with else branches.
@if(condition)— Renders the following content only when the condition is truthy.@else— Optional; rendered when the@ifcondition is false.@elseif(condition)— Optional; additional condition; first matching branch is used.@endif— Ends the conditional block.
Conditions
You can use:- Word operators (safe in HTML):
eq,neq,lt,lte,gt,gte
Example:@if(orders.length gt 0) - Symbols (where allowed):
===,!==,==,!=,<=,>=,<,> - Logic:
and,or, unary! - Property checks:
@if(article.author_avatar),@if(related_articles && related_articles.length)
@elseif and array length:
Loops: @foreach … @endforeach
Repeat a block once per element in an array.
@foreach(item in array)—itemis the variable name for the current element;arrayis an expression that must evaluate to an array (e.g.posts,related_articles).@endforeach— Required; ends the loop.@each(item in array)…@endeach— Same loop under another name; either closer works.@foreach((key, value) in object)— Loop over an object’s keys and values.
{{ item.property }}, @if, nested @foreach, and filters.
The loop variable
Inside every loop, loop describes the current pass:
For example, an
ItemList with a position and no trailing comma:
loop, like the item variable, exists only inside the loop.
Variables set inside a loop
A variable you@set inside a loop keeps its value after @endforeach, and each pass sees the value the previous pass left. Use it for counts and totals:
Variables: @set
Define a variable for use later in the template.
Directives on one line
Directives work on a line of their own or inline, next to other directives and text. These two are the same:@if( @elseif( @else @endif, @foreach( @endforeach, @each( @endeach, @set(, @setSessionItem( @clearSessionItem(, @component( and @yield(:
@extends(…)— On its own line, at the top of the file.@block(…)— On its own line, directly after a tag (</style> @block("head")), or with its@endblockon the same line (<title>@block("title")About@endblock</title>).
ef lint warns about it.
An @ that doesn’t start one of these directives is left as it is, so emails (support@example.com), handles (@yourbrand), CSS at-rules (@media, @font-face, @import) and @ in scripts need no escaping. A word such as @settings or use @set to is text too: a directive needs its (.
Components: @component
Include a reusable component by name, with optional arguments.
Inheritance: @extends, @block, and @yield
Use a base template and override only certain regions.
@yield("name") and @block("name")…@endblock both define named regions in a base layout that child templates can fill. The difference: @yield has no default content (renders empty if not overridden), while @block can include default content as a fallback.
Base template (e.g. layout)
The base defines named blocks that child templates can override:Child template
The child declares which base it extends and redefines one or more blocks:@extends("pageSlug")— Must be at the top; use the base page’s slug.@block("name")…@endblockin the child — Replaces the same-named@blockor@yieldin the base. Only the blocks you define are overridden; the rest of the base layout is used as-is.
@yield vs @block — when to use which
@yield("name") is a slot with no default content — nothing renders if the child does not provide an override. @block("name") default @endblock has optional default content that renders when no child override is provided.
Example base layout using
@yield for required slots and @block for optional ones:
Session storage
You can store and read simple values in the visitor’s session from templates. Use this for things like remembering a choice across requests (e.g. a selected option, a flag) without using the frontend.
Rules:
- Keys may only use letters, numbers, and underscores (
a–z,A–Z,0–9,_). Other characters are stripped. - Values are stored safely (encoded). You can pass strings or numbers; other types are JSON-serialized. There is a size limit per value (~64 KB).
- Clearing: Passing
null(or nothing) tosetSessionItemremoves the key, as does@clearSessionItem('key').
- Lifetime: Session data (including values you store with
setSessionItem) lasts 3 hours from when the session was first created. The timer does not reset on each page load—so after 3 hours the session expires and all stored values are gone. - When it resets: The session is tied to the visitor’s session cookie. It is cleared when:
- the 3-hour lifetime has passed,
- the visitor clears their cookies,
- or they use a different browser or device (new session).
- Use session storage for short-lived, per-visit state (e.g. “has seen this step”, “selected option for this visit”). For long-lived or cross-device data, use a different mechanism (e.g. customer account, database).
Summary
Next: Variables and filters.