Twig Filters: Modifying Variables in Drupal 8 Template Files

Image
Filter

Something that's super fun about my job is that occasionally I get tasked with things like, "Learn how Twig works so you can tell us how it fits into our curriculum plans." And I get to spend some time exploring various new features in Drupal 8, with an eye towards being able help explain them.

Generally, the first place I go looking for new information is the Drupal.org handbook. Though for Drupal 8 this is still very much a work in progress and it's not uncommon to discover there is little to no information about the topic at hand. While it's nice when the information I'm after is just there and ready to go, I also enjoy exploring. I love digging into the code and discovering how things work, and then stepping back and looking at the bigger picture and thinking about how I might explain this to someone elseā€”even future me!

Translating strings in Twig templates

This happened recently, when I needed to learn how to include translatable strings in a Twig template file. Easy enough; there are plenty of examples in Core to review. Simply add the pipe character | followed by t to the string in your Twig file and you're good to go.

Drupal 7:

<div class="my-favorite-things"><?php print t('Mountains, snow, and Tetris.'); ?></div>

Drupal 8:

<div class="my-favorite-things">{{ 'Mountains, snow, and Tetris.'|t }}</div>

That's all well and good, and I could now output translatable strings in my Twig files. But the explorer in me wasn't content. I still wanted answers to questions like, "Where does t come from?", and "How does that work?". So I opened PHPStorm and started digging in.

I didn't know it at first, but the thing that I was looking to understand are what Twig refers to as filters.

Using Filters in Twig Templates

Filters are used to modify variables within a Twig template file. Like PHP functions that perform some manipulation on a given argument and return a string. (In fact, that's exactly what they are once you get below the template layer.) Filters are separated from the variable by a pipe symbol | and may have optional arguments in parentheses. You can also chain multiple filters together. You can see Twig filters in action by checking out our recent Twig Templating series by our friends at KnpUniversity.

There is a list of filters that are part of the Twig engine, and all of these are available when using Twig with Drupal. These filters allow you do things like join arrays of strings together or find the absolute value of a number. See the Twig filter documentation page for more on Twig filters.

And there are Drupal specific filters, like the t filter above, that you can find more information about on the Filters - Modifying Variables In Twig Templates page on Drupal.org. In most cases, new filters are added to provide new functionality that doesn't exist in the core Twig engine, but in some cases Drupal also provides replacements for existing Twig filters that do things in a more Drupal manner.

Okay cool. Filters. Got it.

How Filters Work in Twig Templates

Want to know how filters work? Want to add your own?

When the Twig engine reads in your template file, and encounters a line like the one below it extracts the dynamic content within the double curly braces {{ }}, recognizes that there is one or more pipe symbol in the dynamic content and knows, "I need to apply a filter here, to whatever content preceded the pipe symbol."

<div class="my-favorite-things">{{ 'Mountains, snow, and Tetris.'|t }}</div>

In this example the filter is the t, or translate, filter, which maps directly to calling the PHP t function defined by Drupal. Twig passes in 'Mountains, snow, and Tetris., as the first argument to the function, and then inserts the string returned from the function into the place of the dynamic placeholder in your Twig template. Filters, are just PHP callables that Twig invokes on our behalf.

You can't however just go about calling any PHP function willy-nilly. {{ 'Big cheese.'|drupal_rebuild }} for example isn't going to call the drupal_rebuild() function, despite that fact that it is indeed defined. Rather, you're limited to using the functions/filters that have been registered with Twig. This is done by implementing the Twig_Extension::getFilters() method and returning an array of \Twig_SimpleFilter or \Twig_Filter_Function objects, one for each new filter you want to declare. See \Drupal\Core\Template\TwigExtension::getFilters(), where Drupal core adds in all its extra filters like t, and drupal_escape.

If you want to add your own, the best example I've seen for doing this is in the core/modules/system/tests/twig_extension_test/ module.

A Note to My Future Self

At the beginning of this post I said that I started by taking a look at the Drupal.org handbook for information about Twig filters, and didn't find much. So I've pieced this information together through various other sources including reading the source code, and this excellent documentation on GitHub. They say you've truly mastered a subject when you can explain it to others and they understand it. So, future Joe, if you're ever curious about Twig filters in Drupal 8 I've documented them all here on Drupal.org.

About us

Drupalize.Me is the best resource for learning Drupal online. We have an extensive library covering multiple versions of Drupal and we are the most accurate and up-to-date Drupal resource. Learn more