caa18e5 Jun 6, 2014
@jrudolph @sirthias
197 lines (121 sloc) 7.78 KB



Twirl has moved back home to play where all future versions will live. The new official version only supports sbt >= 0.13.5. If you depend on an older version of sbt read on, otherwise, you will probably be better off directly heading over to the new repository.

Twirl is the Play Framework Scala template engine, repackaged for stand-alone use. This project provides an SBT plugin that lets you use Twirl in your Scala applications without any additional dependencies on the Play Framework.

The Scala template engine (which we dubbed Twirl, see below) provided by Play 2.0 enables type-safe templating that integrates seamlessly into your Scala applications. Templates are text files containing a mix of "markup" and Scala code. At compile time the Twirl compiler translates them into actual Scala source files, which are then picked up by the Scala compiler and compiled together with the rest of your application sources into regular .class files. On a type level each template is just a function from a number of (strongly typed) input values to a result object.

The Twirl SBT plugin smoothly integrates templating support into your Scala builds. It supports triggered compilation (via SBTs ~ operator) as well as hot reloading via sbt-revolver.

Note: The large majority of the code within this project, i.e. the twirl-api, the twirl-compiler and significant portions of the SBT plugin are nothing but verbatim copies of the respective code pieces from the Play Framework Repository. All credits and copyrights for these belong to Play framework team.


sbt-twirl requires SBT 0.13 or 0.12. Add the following dependency to your project/*.sbt file (e.g. project/plugins.sbt):

// needed because sbt-twirl depends on twirl-compiler which is only available
// at
resolvers += "spray repo" at ""

addSbtPlugin("io.spray" % "sbt-twirl" % "0.7.0")

Then, in your build.sbt:


If you use SBTs full-configuration you need to:

import twirl.sbt.TwirlPlugin._

and then add the Twirl.settings to all (sub-)projects containing Twirl templates.


Twirl template files are expected to live in the twirl subdirectory of your source directory, e.g. src/main/twirl. They have to be named {template-name}.scala.{ext}, whereby ext can be either html, xml or txt (more extensions might be supported in the future).



Template Syntax

The internal template syntax is documented here. Currently the Twirl engine does not differ from the original Play Scala Template Engine in any way.

Template Rendering

To your Scala code a template is an object providing the following methods:

def apply(: A, b: B, ...): R

def render(a: A, b: B, ...): R = apply(a, b, ...)

def f: (A, B) => R = (a, b) => apply(a, b)

whereby A and B are the parameter types you have specified in the first line of your template. R is the result type, which is either twirl.api.Html, twirl.api.Txt or twirl.api.Xml, depending on the extension of your template. All result types are defined in this file, please check it out to understand what interface the respective result type offers.

From your Scala code you "render" a template by simply calling one of its methods, e.g., the template defined in {project-directory}/src/main/twirl/index.scala.html would could be called with:

html.index.render("Bob", 42)

and the template {project-directory}/src/main/twirl/org/example/hello.scala.txt could be called with:

org.example.txt.hello("Fred", "Astair")

Package Names

As you already might have guessed from the last example above sub directories underneath the ../twirl template directory are turned into package names for the created template objects. So, if you place a template in the {project-directory}/src/main/twirl/org/example/ directory it will have the package org.example.html, org.example.txt or org.example.xml, depending on the file extension.

So, for example, if you'd like to include a template {project-directory}/src/main/twirl/org/example/Foo.scala.html from another template you would say @org.example.html.Foo().


sbt-twirl currently offers the following customization options:

  1. twirlImports = SettingKey[Seq[String]]: lets you specify one or more imports that are to be made available to the Scala source in your template files.

    For example:

    twirlImports := Seq("org.example.util._", "com.mycompany.DbTools")

    will be turned into the following import statements:

    import org.example.util._
    import com.mycompany.DbTools

    In addition the strings in twirlImports can contain a %format% placeholder, which is replaced with the template file extension. This way you can target imports for specific template types.

  2. twirlSourceCharset = SettingKey[Charset]: lets you specify the java.nio.charset.Charset to use when reading twirl template sources and writing their corresponding .scala files. The default value is the UTF-8 charset.

  3. twirlRecompilationLogger = TaskKey[(File, File) => Unit]: lets you specify a custom logging function to call when one twirl file is being recompiled. For each file that needs recompilation, the function is invoked with the source and target file. Per default, one line is logged per file. E.g. to switch off logging completely you can use a setting Twirl.twirlRecompilationLogger := ((_, _) => ()).


The /example directory of this project contains a tiny, stand-alone SBT 0.11.2 example project that you can look at or use as the basis for your own endeavors.

Why "Twirl" ?

As a replacement for the rather unwieldy name "Play Framework Scala template engine" we were looking for something shorter with a bit of "punch" and liked Twirl as a reference to the template languages "magic" character @, which is sometimes also called "twirl".

Known Issues

Scala compilation errors in templates will be shown twice. Once as the verbatim error message as generated by the compiler for the Scala source file created by the Twirl compiler and once mapped to the actual location in the template source file. Suppressing the first message probably requires a fix in SBT.


Just like the Play Framework Scala template engine Twirl is licensed under the Apache License 2.0.


All credits are to go to the Play developers who devised the template language and provided its implementation! Thanks to @4lex1v for updating twirl to the latest upstream version which supports sbt 0.13.

Patch Policy

Feedback and contributions to the project, no matter what kind, are always very welcome. However, patches can only be accepted from their original author. Along with any patches, please state that the patch is your original work and that you license the work to the twirl project under the project’s open source license.