You are viewing the documentation for Play 1. The documentation for Play 2 is here.

Built-in template tags

These are the built-in tags that are available in addition to the core template engine syntax.

There is a separate Java extensions manual page.


The a tag inserts an HTML link to a controller action.

#{a @Application.logout()}Disconnect#{/a}

Rendered as:

<a href="/application/logout">Disconnect</a>

If the action you try to call does not have any route able to invoke it using a GET method, Play will automatically generate a hidden form that will be submitted on link click using JavaScript.


Renders a hidden input field containing a generated token that you can use in any form. See the Cross-Site Request Forgery section.

#{authenticityToken /}

Rendered as:

<input type="hidden" name="authenticityToken" value="1c6d92fed96200347f06b7c5e1a3a28fa258ef7c">


Caches the tag body using the play.cache.Cache API, for the cache key specified by the tag parameter.

#{cache 'startTime'}
   ${new java.util.Date()}

The body is cached indefinitely by default, but you can specify an expiration duration with the for parameter.

#{cache 'currentTime', for:'3s'}
   ${new java.util.Date()}


Used with template inheritance, this tag inserts the evaluated sub-template’s contents.

<!-- common header here -->
<div id="content">
    #{doLayout /}
<!-- common footer here -->


Of course used with the if tag.

#{if user}
    Connected user is ${user}
    Please log in

However, you can also use it with the list tag and it will be executed if the list is empty.

#{list items:task, as:'task'}
    Nothing to do...


#{if tasks.size() > 1}
    Busy tasklist
#{elseif tasks}
    One task on the list
    Nothing to do

As for else, you can use it with the list tag.


Outputs the validation error message, if present, for the field specified by the tag parameter.

#{error ''/}

You can use the optional field parameter to use a different field’s error message. This is useful when you want several fields to share a common error message.

#{error 'contact.street',  field:'contact.address'/}
#{error '',    field:'contact.address'/}
#{error '', field:'contact.address'/}


Outputs the text hasError if there is a validation error for the field specified by the tag parameter. This is useful for setting a CSS class for input fields with errors:

<input name="name" class="#{errorClass 'name'/}">

which is equivalent to:

<input name="name" class="${errors.forKey('name') ? 'hasError' : ''}">


Iterates over the current validation errors.


The tag defines implicit variables in its body.

    <tr class="${error_parity}"><td>${error_index}</td><td>${error}</td></tr>


Makes the template inherit another template.

#{extends 'main.html' /}


The field tag is a helper, based on the spirit of the Don’t Repeat Yourself. It works this way:

Instead of writing this:

  <input type="text" id="user_name" name="" value="${user?.name}" class="${errors.forKey('') ? 'has_error' : ''}">
  <span class="error">${errors.forKey('')}</span>

You can just write:

#{field ''}
  <input type="text" id="${}" name="${}" value="${field.value}" class="${field.errorClass}">
  <span class="error">${field.error}</span>

So you don’t repeat again and again.


Inserts a form tag. The HTTP method is guessed from the route, and defaults to POST. If there are both GET and POST routes configured for the URL, the tag will default to using the first route defined in routes.

Charset encoding is always ‘utf-8’.

#{form @Client.create() , id:'creationForm', enctype:'multipart/form-data' }

Rendered as:

<form action="/client/create" id="creationForm" method="POST" accept-charset="utf-8" enctype="multipart/form-data">


Retrieves a value defined with a set tag. You may use the get/set mechanism to exchange values between templates, layouts and sub-templates.

    <title>#{get 'title' /}

You can also use the get tag in the following way, which will display “Homepage” if title has not been specified.

    <title>#{get 'title'}Homepage #{/} 


Exports localized messages in JavaScript. Localized messages are available from your JavaScript code using the i18n() function.

Define your translations in the conf/messages file.

hello_world=Hello, World !
hello_someone=Hello %s !

Include the messages in your template (or layout) page:

#{i18n /}

And retrieve keys from JavaScript:

alert(i18n('hello_someone', 'John'));


Evaluates the given test, and if true, evaluates the tag body.

#{if user.countryCode == 'en"' }
    Connected user is ${user}

Using composite conditions:

#{if ( request.actionMethod == 'administer'  && user.isAdmin() ) }
    You are admin, allowed to administer.


Renders the tag body if there is a validation error for the input field field named by the tag parameter.

#{ifError ''}
    User name is invalid: 
    #{error '' /}


Renders the tag body if any field has a validation error.

  <p>Error(s) found!</p>


Cleaner alternative to #{if !condition}

#{ifnot tasks}
    No tasks today


Includes another template. All of the current template’s variables are directly available in the included template.

<div id="tree">
    #{include 'tree.html' /}


The #{jsAction /} tag returns a JavaScript function which constructs a URL based on a server action and free variables. It does not perform an AJAX request; these have to be done by hand using the returned URL.

Let’s see an example:

GET     /users/{id}

Now you can import this route client side:

<script type="text/javascript">
    var showUserAction = #{jsAction':id') /}
    var displayUserDetail = function(userId) {
        $('userDetail').load( showUserAction({id: userId}) )


Iterates over an object collection.

#{list items:products, as:'product'}

The tag defines implicit variables in its body. The variable names are prefixed with the loop variable name.

#{list items:products, as:'product'}
    <span class="${product_parity}">${product_index}. ${product}</span>
    ${product_isLast ? '' : '-'}

The items parameter is optional and can be replaced by the default arg argument.

So you can rewrite:

#{list items:users, as:'user'}


#{list users, as:'user'}

for loops are easy to create using Groovy range object:

#{list items:0..10, as:'i'}
#{list items:'a'..'z', as:'letter'}
    ${letter} ${letter_isLast ? '' : '|' }

The as parameter is optional as well. It uses _ as default variable name:

#{list users}


Insert an option tag in the template.

#{option} ${} #{/option}

Will output:

<option value="42">jto</option>h2. <a name="script">script</a>

Inserts a script tag in the template. By convention, the tag refers to a script in /public/javascripts

The src parameter can be replaced by the default arg argument.

#{script 'jquery-1.4.2.min.js' /}
#{script id:'datepicker' , src:'ui/ui.datepicker.js', charset:'utf-8' /}


Renders the template specified by the path in the tag parameter. The path is either absolute, or relative to /app/views

#{render 'Application/other.html'/}


Insert a select tag in the template.

Any unknow attribute will be considered as an HTML attribute, and rendered "as is"

#{select 'booking.beds', value:2, id:'select1'}
	#{option 1}One king-size bed#{/option}
	#{option 2}Two double beds#{/option}
	#{option 3}Three beds#{/option}

Will output:

<select name="booking.beds" size="1" id="select1" >
  <option value="1">One king-size bed</option>
  <option value="2" selected="selected">Two double beds</option>
  <option value="3">Three beds</option>

This tag can generate options using items attribute.

For example, giving a list of User, each having a name attribute:

#{select 'users', items:users, valueProperty:'id', labelProperty:'name', value:'User-5', class:"test", id:'select2' /}

Will output:

<select name="users" size="1" class="test" id="select2" >
  <option value="0" >User-0</option>
  <option value="1" >User-1</option>            
  <option value="2" >User-2</option>            
  <option value="3" >User-3</option>
  <option value="4" >User-4</option>
  <option value="5" selected="selected">User-5</option>


Define a value which can be retrieved in the same template or any layout with the get tag.

#{set title:'Admin' /}
#{set style:'2columns' /}

You can also use variables:

#{set title:'Profile of ' + user.login /}

You can define the value of variables in the body:

#{set 'title'}
    Profile of ${user.login}


Inserts a link tag in the template. By convention, the tag refers to a CSS file in /public/stylesheets

The src parameter can be replaced by the default arg argument.

#{stylesheet 'default.css' /}
#{stylesheet id:'main', media:'print', src:'print.css', title:'Print stylesheet' /}


Disables HTML escaping in template output, like the raw() Java extension, but for the whole tag body.


In this example, the first line outputs &amp; while the second line outputs an ampersand.