diff --git a/core/core.services.yml b/core/core.services.yml index ea1a56b..ec994a2 100644 --- a/core/core.services.yml +++ b/core/core.services.yml @@ -1425,7 +1425,7 @@ services: class: Drupal\Core\Extension\InfoParser twig: class: Drupal\Core\Template\TwigEnvironment - arguments: ['@app.root', '@cache.default', '@twig.loader', '%twig.config%'] + arguments: ['@app.root', '@cache.default', '%twig_extension_hash%', '@twig.loader', '%twig.config%'] tags: - { name: service_collector, tag: 'twig.extension', call: addExtension } twig.extension: diff --git a/core/lib/Drupal/Core/CoreServiceProvider.php b/core/lib/Drupal/Core/CoreServiceProvider.php index 7e02c80..3d1b350 100644 --- a/core/lib/Drupal/Core/CoreServiceProvider.php +++ b/core/lib/Drupal/Core/CoreServiceProvider.php @@ -19,6 +19,7 @@ use Drupal\Core\DependencyInjection\Compiler\StackedKernelPass; use Drupal\Core\DependencyInjection\Compiler\StackedSessionHandlerPass; use Drupal\Core\DependencyInjection\Compiler\RegisterStreamWrappersPass; +use Drupal\Core\DependencyInjection\Compiler\TwigExtensionPass; use Drupal\Core\DependencyInjection\ServiceProviderInterface; use Drupal\Core\DependencyInjection\ContainerBuilder; use Drupal\Core\DependencyInjection\Compiler\ModifyServiceDefinitionsPass; @@ -78,6 +79,8 @@ public function register(ContainerBuilder $container) { $container->addCompilerPass(new RegisterStreamWrappersPass()); $container->addCompilerPass(new GuzzleMiddlewarePass()); + $this->addCompilerPass(new TwigExtensionPass()); + // Add a compiler pass for registering event subscribers. $container->addCompilerPass(new RegisterKernelListenersPass(), PassConfig::TYPE_AFTER_REMOVING); diff --git a/core/lib/Drupal/Core/DependencyInjection/Compiler/TwigExtensionPass.php b/core/lib/Drupal/Core/DependencyInjection/Compiler/TwigExtensionPass.php new file mode 100644 index 0000000..e2a0edf --- /dev/null +++ b/core/lib/Drupal/Core/DependencyInjection/Compiler/TwigExtensionPass.php @@ -0,0 +1,30 @@ +findTaggedServiceIds('twig.extension') as $service_id) { + $twig_extension_hash .= $container->getDefinition($service_id)->getClass(); + } + + $container->setParameter('twig_extension_hash', $twig_extension_hash); + } + +} diff --git a/core/lib/Drupal/Core/Template/TwigEnvironment.php b/core/lib/Drupal/Core/Template/TwigEnvironment.php index a1abf84..fbc14bf 100644 --- a/core/lib/Drupal/Core/Template/TwigEnvironment.php +++ b/core/lib/Drupal/Core/Template/TwigEnvironment.php @@ -52,6 +52,13 @@ class TwigEnvironment extends \Twig_Environment { protected $templateClasses; /** + * The twig extension hash, which is used to invalidate twig templates. + * + * @var string + */ + protected $twigExtensionHash; + + /** * Constructs a TwigEnvironment object and stores cache and storage * internally. * @@ -59,13 +66,16 @@ class TwigEnvironment extends \Twig_Environment { * The app root. * @param \Drupal\Core\Cache\CacheBackendInterface $cache * The cache bin. + * @param string $twig_extension_hash + * The twig extension hash. * @param \Twig_LoaderInterface $loader * The Twig loader or loader chain. * @param array $options * The options for the Twig environment. */ - public function __construct($root, CacheBackendInterface $cache, \Twig_LoaderInterface $loader = NULL, $options = array()) { + public function __construct($root, CacheBackendInterface $cache, $twig_extension_hash, \Twig_LoaderInterface $loader = NULL, $options = array()) { $this->cache_object = $cache; + $this->twigExtensionHash = $twig_extension_hash; // Ensure that twig.engine is loaded, given that it is needed to render a // template because functions like TwigExtension::escapeFilter() are called. @@ -125,13 +135,7 @@ public function getCacheFilename($name) { // Just check the list of loaded extensions once. if (!isset($this->templateCacheFilenamePrefix)) { - $extensions = ''; - foreach ($this->extensions as $extension) { - $r = new \ReflectionObject($extension); - $extensions .= $r->getFilename(); - } - - $this->templateCacheFilenamePrefix = hash('crc32b', $extensions . \Drupal::VERSION . Settings::get('deployment_identifier', \Drupal::VERSION)); + $this->templateCacheFilenamePrefix = hash('crc32b', $this->twigExtensionHash . \Drupal::VERSION . Settings::get('deployment_identifier', \Drupal::VERSION)); } // The first part is what is invalidated.