vendor/symfony/twig-bridge/DataCollector/TwigDataCollector.php line 35

Open in your IDE?
  1. <?php
  2. /*
  3.  * This file is part of the Symfony package.
  4.  *
  5.  * (c) Fabien Potencier <fabien@symfony.com>
  6.  *
  7.  * For the full copyright and license information, please view the LICENSE
  8.  * file that was distributed with this source code.
  9.  */
  10. namespace Symfony\Bridge\Twig\DataCollector;
  11. use Symfony\Component\HttpFoundation\Request;
  12. use Symfony\Component\HttpFoundation\Response;
  13. use Symfony\Component\HttpKernel\DataCollector\DataCollector;
  14. use Symfony\Component\HttpKernel\DataCollector\LateDataCollectorInterface;
  15. use Twig\Environment;
  16. use Twig\Error\LoaderError;
  17. use Twig\Markup;
  18. use Twig\Profiler\Dumper\HtmlDumper;
  19. use Twig\Profiler\Profile;
  20. /**
  21.  * @author Fabien Potencier <fabien@symfony.com>
  22.  *
  23.  * @final
  24.  */
  25. class TwigDataCollector extends DataCollector implements LateDataCollectorInterface
  26. {
  27.     private $profile;
  28.     private $twig;
  29.     private $computed;
  30.     public function __construct(Profile $profileEnvironment $twig null)
  31.     {
  32.         $this->profile $profile;
  33.         $this->twig $twig;
  34.     }
  35.     /**
  36.      * {@inheritdoc}
  37.      */
  38.     public function collect(Request $requestResponse $response\Throwable $exception null)
  39.     {
  40.     }
  41.     /**
  42.      * {@inheritdoc}
  43.      */
  44.     public function reset()
  45.     {
  46.         $this->profile->reset();
  47.         $this->computed null;
  48.         $this->data = [];
  49.     }
  50.     /**
  51.      * {@inheritdoc}
  52.      */
  53.     public function lateCollect()
  54.     {
  55.         $this->data['profile'] = serialize($this->profile);
  56.         $this->data['template_paths'] = [];
  57.         if (null === $this->twig) {
  58.             return;
  59.         }
  60.         $templateFinder = function (Profile $profile) use (&$templateFinder) {
  61.             if ($profile->isTemplate()) {
  62.                 try {
  63.                     $template $this->twig->load($name $profile->getName());
  64.                 } catch (LoaderError $e) {
  65.                     $template null;
  66.                 }
  67.                 if (null !== $template && '' !== $path $template->getSourceContext()->getPath()) {
  68.                     $this->data['template_paths'][$name] = $path;
  69.                 }
  70.             }
  71.             foreach ($profile as $p) {
  72.                 $templateFinder($p);
  73.             }
  74.         };
  75.         $templateFinder($this->profile);
  76.     }
  77.     public function getTime()
  78.     {
  79.         return $this->getProfile()->getDuration() * 1000;
  80.     }
  81.     public function getTemplateCount()
  82.     {
  83.         return $this->getComputedData('template_count');
  84.     }
  85.     public function getTemplatePaths()
  86.     {
  87.         return $this->data['template_paths'];
  88.     }
  89.     public function getTemplates()
  90.     {
  91.         return $this->getComputedData('templates');
  92.     }
  93.     public function getBlockCount()
  94.     {
  95.         return $this->getComputedData('block_count');
  96.     }
  97.     public function getMacroCount()
  98.     {
  99.         return $this->getComputedData('macro_count');
  100.     }
  101.     public function getHtmlCallGraph()
  102.     {
  103.         $dumper = new HtmlDumper();
  104.         $dump $dumper->dump($this->getProfile());
  105.         // needed to remove the hardcoded CSS styles
  106.         $dump str_replace([
  107.             '<span style="background-color: #ffd">',
  108.             '<span style="color: #d44">',
  109.             '<span style="background-color: #dfd">',
  110.             '<span style="background-color: #ddf">',
  111.         ], [
  112.             '<span class="status-warning">',
  113.             '<span class="status-error">',
  114.             '<span class="status-success">',
  115.             '<span class="status-info">',
  116.         ], $dump);
  117.         return new Markup($dump'UTF-8');
  118.     }
  119.     public function getProfile()
  120.     {
  121.         if (null === $this->profile) {
  122.             $this->profile unserialize($this->data['profile'], ['allowed_classes' => ['Twig_Profiler_Profile''Twig\Profiler\Profile']]);
  123.         }
  124.         return $this->profile;
  125.     }
  126.     private function getComputedData(string $index)
  127.     {
  128.         if (null === $this->computed) {
  129.             $this->computed $this->computeData($this->getProfile());
  130.         }
  131.         return $this->computed[$index];
  132.     }
  133.     private function computeData(Profile $profile)
  134.     {
  135.         $data = [
  136.             'template_count' => 0,
  137.             'block_count' => 0,
  138.             'macro_count' => 0,
  139.         ];
  140.         $templates = [];
  141.         foreach ($profile as $p) {
  142.             $d $this->computeData($p);
  143.             $data['template_count'] += ($p->isTemplate() ? 0) + $d['template_count'];
  144.             $data['block_count'] += ($p->isBlock() ? 0) + $d['block_count'];
  145.             $data['macro_count'] += ($p->isMacro() ? 0) + $d['macro_count'];
  146.             if ($p->isTemplate()) {
  147.                 if (!isset($templates[$p->getTemplate()])) {
  148.                     $templates[$p->getTemplate()] = 1;
  149.                 } else {
  150.                     ++$templates[$p->getTemplate()];
  151.                 }
  152.             }
  153.             foreach ($d['templates'] as $template => $count) {
  154.                 if (!isset($templates[$template])) {
  155.                     $templates[$template] = $count;
  156.                 } else {
  157.                     $templates[$template] += $count;
  158.                 }
  159.             }
  160.         }
  161.         $data['templates'] = $templates;
  162.         return $data;
  163.     }
  164.     /**
  165.      * {@inheritdoc}
  166.      */
  167.     public function getName(): string
  168.     {
  169.         return 'twig';
  170.     }
  171. }