Last active
April 22, 2022 18:05
-
-
Save dsasser/2e5d0ae10cc190d9f17240c425b76d11 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace Drupal\module\Plugin\Preprocess; | |
use Drupal\Core\Cache\CacheableMetadata; | |
use Drupal\Core\Render\Element; | |
use Drupal\preprocess\PreprocessPluginBase; | |
use Symfony\Component\DependencyInjection\ContainerInterface; | |
use Drupal\Core\Plugin\ContainerFactoryPluginInterface; | |
/** | |
* Base class for preprocess plugins. | |
* | |
* Define any helper functions needed in plugins within this class. | |
*/ | |
class PreprocessBase extends PreprocessPluginBase implements ContainerFactoryPluginInterface { | |
/** | |
* Whether to bubble descendant cache metadata to the top level. | |
* | |
* @var bool | |
*/ | |
public $bubbleCache = FALSE; | |
/** | |
* Constructs a new PreprocessBase object. | |
* | |
* @param array $configuration | |
* A configuration array containing information about the plugin instance. | |
* @param string $plugin_id | |
* The plugin_id for the plugin instance. | |
* @param mixed $plugin_definition | |
* The plugin implementation definition. | |
* @param \Symfony\Component\DependencyInjection\ContainerInterface $container | |
* The dependency injection container. | |
*/ | |
public function __construct(array $configuration, $plugin_id, $plugin_definition, ContainerInterface $container) { | |
parent::__construct($configuration, $plugin_id, $plugin_definition); | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public static function create(ContainerInterface $container, array $configuration, $plugin_id, $plugin_definition) { | |
return new static( | |
$configuration, | |
$plugin_id, | |
$plugin_definition, | |
$container, | |
); | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function preprocess(array $variables): array { | |
// Bubble cache metadata if configured to do so. | |
if ($this->bubbleCache) { | |
$cache = $this->bubbleCache($variables, CacheableMetadata::createFromRenderArray($variables)); | |
$cache->applyTo($variables); | |
} | |
return $variables; | |
} | |
/** | |
* Ensures that all cache metadata for nested elements bubble to response. | |
* | |
* Some templates do not print the content render array choosing to instead | |
* print variables created during preprocessing. When this happens, cache | |
* metadata is lost causing improper cache behavior. This method does the work | |
* of grabbing cache metadata from a render array regardless of the depth of | |
* the #cache key in the array. | |
* | |
* @param array $variables | |
* Elements to pull cache metadata from. | |
* @param \Drupal\Core\Cache\CacheableMetadata $cache | |
* Cache metadata for the current element. | |
* | |
* @return \Drupal\Core\Cache\CacheableMetadata | |
* Updated cache metadata. | |
*/ | |
public function bubbleCache(array $variables, CacheableMetadata $cache) { | |
foreach (@Element::children($variables) as $key) { | |
if (!empty($variables[$key])) { | |
$cache = $this->bubbleCache($variables[$key], $cache); | |
} | |
} | |
return $cache->merge(CacheableMetadata::createFromRenderArray($variables)); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment