Skip to content

[Cookbook][Templating] custom Twig Extension #1215

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 7 commits into from
Apr 11, 2012
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions book/templating.rst
Original file line number Diff line number Diff line change
Expand Up @@ -1334,6 +1334,7 @@ Learn more from the Cookbook

* :doc:`/cookbook/templating/PHP`
* :doc:`/cookbook/controller/error_pages`
* :doc:`/cookbook/templating/twig_extension`

.. _`Twig`: http://twig.sensiolabs.org
.. _`KnpBundles.com`: http://knpbundles.com
Expand Down
1 change: 1 addition & 0 deletions cookbook/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ Cookbook

templating/global_variables
templating/PHP
templating/twig_extension

logging/monolog
logging/monolog_email
Expand Down
1 change: 1 addition & 0 deletions cookbook/map.rst.inc
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,7 @@

* :doc:`/cookbook/templating/global_variables`
* :doc:`/cookbook/templating/PHP`
* :doc:`/cookbook/templating/twig_extension`

* **Logging**

Expand Down
128 changes: 128 additions & 0 deletions cookbook/templating/twig_extension.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,128 @@
.. index::
single: Twig extensions

How to write a custom Twig Extension
====================================

The main motivation for writing an extension is to move often used code
into a reusable class like adding support for internationalization.
An extension can define tags, filters, tests, operators, global variables,
functions, and node visitors.

Creating an extension also makes for a better separation of code that is
executed at compilation time and code needed at runtime. As such, it makes
your code faster.

.. tip::

Before writing your own extensions, have a look at the `Twig official extension repository`_.

Create the Extension Class
--------------------------

To get your custom functionality you must first create a Twig Extension class.
As an example we will create a price filter to format a given number into price::

// src/Acme/DemoBundle/Twig/AcmeExtension.php

namespace Acme\DemoBundle\Twig;

use Twig_Extension;
use Twig_Filter_Method;
use Twig_Function_Method;

class AcmeExtension extends Twig_Extension
{
public function getFilters()
{
return array(
'price' => new Twig_Filter_Method($this, 'priceFilter'),
);
}

public function priceFilter($number, $decimals = 0, $decPoint = '.', $thousandsSep = ',')
{
$price = number_format($number, $decimals, $decPoint, $thousandsSep);
$price = '$' . $price;

return $price;
}

public function getName()
{
return 'acme_extension';
}
}

.. tip::

Along with custom filters, you can also add custom `functions` and register `global variables`.

Register an Extension as a Service
-------------------------------

Now you must let Service Container know about your newly created Twig Extension:

.. configuration-block::

.. code-block:: xml

<!-- src/Acme/DemoBundle/Resources/config/services.xml -->
<services>
<service id="acme.twig.acme_extension" class="Acme\DemoBundle\Twig\AcmeExtension">
<tag name="twig.extension" />
</service>
</services>

.. code-block:: yaml

# src/Acme/DemoBundle/Resources/config/services.yml
services:
acme.twig.acme_extension:
class: Acme\DemoBundle\Twig\AcmeExtension
tags:
- { name: twig.extension }

.. code-block:: php

// src/Acme/DemoBundle/Resources/config/services.php
use Symfony\Component\DependencyInjection\Definition;

$acmeDefinition = new Definition('\Acme\DemoBundle\Twig\AcmeExtension');
$acmeDefinition->addTag('twig.extension');
$container->setDefinition('acme.twig.acme_extension', $acmeDefinition);

.. note::

Keep in mind that Twig Extensions are not lazily loaded. This means that
there's a higher chance that you'll get a **CircularReferenceException**
or a **ScopeWideningInjectionException** if any services
(or your Twig Extension in this case) are dependent on the request service.
For more information take a look at :doc:`/cookbook/service_container/scopes`.

Using the custom Extension
--------------------------

Using your newly created Twig Extension is no different than any other:

.. code-block:: jinja

{# outputs $5,500.00 #}
{{ '5500' | price }}

Passing other arguments to your filter:

.. code-block:: jinja

{# outputs $5500,2516 #}
{{ '5500.25155' | price(4, ',', '') }}

Learning further
----------------

For a more in-depth look into Twig Extensions, please take a look at the `Twig extensions documentation`_.

.. _`Twig official extension repository`: http://github.com/fabpot/Twig-extensions
.. _`Twig extensions documentation`: http://twig.sensiolabs.org/doc/extensions.html
.. _`global variables`: http://twig.sensiolabs.org/doc/extensions.html#globals
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The Twig doc has been refactored on Friday. The new link is http://twig.sensiolabs.org/doc/advanced.html#creating-an-extension

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks! - fixed in sha: fe6632b, though some of the new hashes changed to ids, which is kind of a bummer :/

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also just ran the link checker and fixes some more - so the whole docs should be in good shape now.

.. _`functions`: http://twig.sensiolabs.org/doc/extensions.html#functions
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy