I would like to define a global variable for twig, which would be accessible from any template.
I can create a global variable in symfony's config/packages/twig.yaml
, but I need it to be a value obtained from the database.
In the documentation for twig it says to use this code:
$twig = new Twig_Environment($loader);
$twig->addGlobal('name', 'value');
Where should I use this code so this varible is available for every template?
If you are using Twig in another project, you can set your globals directly in the environment: $twig = new Twig_Environment($loader); $twig->addGlobal('myStuff', $someVariable); And then use {{ myStuff }} anywhere in your application.
In Twig templates variables can be accessed using double curly braces notation {{ variableName }} .
The global Keyword Normally, when you create a variable inside a function, that variable is local, and can only be used inside that function. To create a global variable inside a function, you can use the global keyword.
Accessing a Global VariableThe window is the global object in the browser environment. Any property attached to the window object can be accessed from any script on the web page, including the script for the React app. Since window is a global object, the React code can also access its properties, as shown below.
A relatively clean way of doing would be to add an event subscriber that would inject the variables globally before the controllers are instantiated.
The problem of doing in the controller, as one of the comments suggested, is that your globals wouldn't be global at all, but defined only for that controller.
You could do something like this:
// src/Twig/TwigGlobalSubscriber.php
use Doctrine\ORM\EntityManager;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
use Symfony\Component\HttpKernel\KernelEvents;
use Twig\Environment;
class TwigGlobalSubscriber implements EventSubscriberInterface {
/**
* @var \Twig\Environment
*/
private $twig;
/**
* @var \Doctrine\ORM\EntityManager
*/
private $manager;
public function __construct( Environment $twig, EntityManager $manager ) {
$this->twig = $twig;
$this->manager = $manager;
}
public function injectGlobalVariables( GetResponseEvent $event ) {
$whatYouWantAsGlobal = $this->manager->getRepository( 'SomeClass' )->findBy( [ 'some' => 'criteria' ] );
$this->twig->addGlobal( 'veryGlobal', $whatYouWantAsGlobal[0]->getName() );
}
public static function getSubscribedEvents() {
return [ KernelEvents::CONTROLLER => 'injectGlobalVariables' ];
}
}
The DB interaction I left deliberately fuzzy, since only you know exactly what do you want to retrieve from there. But you are injecting the EntityManager
on this subscriber, so it's only a matter of retrieving the appropriate repository and perform the appropriate search.
Once this is done, you could simply do from your twig templates something like:
<p>I injected a rad global variable: <b>{{ veryGlobal }}</b></p>
Symfony 5.4
service.yml
:
App\Twig\TwigGlobalSubscriber:
tags:
- { name: kernel.event_listener, event: kernel.request }
SysParams - my service takes data from the database
src\Twig\TwigGlobalSubscriber.php
<?php
namespace App\Twig;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\HttpKernel\KernelEvents;
use Twig\Environment;
use App\Service\SysParams;
class TwigGlobalSubscriber implements EventSubscriberInterface {
private $twig;
public function __construct( Environment $twig, SysParams $sysParams ) {
$this->twig = $twig;
$this->sysParams = $sysParams;
}
public function injectGlobalVariables() {
$base_params = $this->sysParams->getBaseForTemplate();
foreach ($base_params as $key => $value) {
$this->twig->addGlobal($key, $value);
}
}
public static function getSubscribedEvents() {
return [ KernelEvents::CONTROLLER => 'injectGlobalVariables' ];
}
public function onKernelRequest()
{
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With