From e770c3846f74e5c3d43b3d258e712f5feb3dbd0f Mon Sep 17 00:00:00 2001 From: Alex Pott <alex.a.pott@googlemail.com> Date: Mon, 25 Jan 2016 13:45:23 +0000 Subject: [PATCH] Issue #2567561 by Sagar Ramgade, mbaynton, Cottser, gnuget, Wim Leers: Captioned elements and their children are removed when theme debugging on --- .../src/Plugin/Filter/FilterCaption.php | 18 +-- .../src/Tests/FilterCaptionTwigDebugTest.php | 109 ++++++++++++++++++ 2 files changed, 119 insertions(+), 8 deletions(-) create mode 100644 core/modules/filter/src/Tests/FilterCaptionTwigDebugTest.php diff --git a/core/modules/filter/src/Plugin/Filter/FilterCaption.php b/core/modules/filter/src/Plugin/Filter/FilterCaption.php index 76a11258303e..627379e8ace3 100644 --- a/core/modules/filter/src/Plugin/Filter/FilterCaption.php +++ b/core/modules/filter/src/Plugin/Filter/FilterCaption.php @@ -72,16 +72,18 @@ public function process($text, $langcode) { $altered_html = drupal_render($filter_caption); // Load the altered HTML into a new DOMDocument and retrieve the element. - $updated_node = Html::load($altered_html)->getElementsByTagName('body') + $updated_nodes = Html::load($altered_html)->getElementsByTagName('body') ->item(0) - ->childNodes - ->item(0); + ->childNodes; - // Import the updated node from the new DOMDocument into the original - // one, importing also the child nodes of the updated node. - $updated_node = $dom->importNode($updated_node, TRUE); - // Finally, replace the original node with the new node. - $node->parentNode->replaceChild($updated_node, $node); + foreach ($updated_nodes as $updated_node) { + // Import the updated node from the new DOMDocument into the original + // one, importing also the child nodes of the updated node. + $updated_node = $dom->importNode($updated_node, TRUE); + $node->parentNode->insertBefore($updated_node, $node); + } + // Finally, remove the original data-caption node. + $node->parentNode->removeChild($node); } $result->setProcessedText(Html::serialize($dom)) diff --git a/core/modules/filter/src/Tests/FilterCaptionTwigDebugTest.php b/core/modules/filter/src/Tests/FilterCaptionTwigDebugTest.php new file mode 100644 index 000000000000..8b3d7cabbd2b --- /dev/null +++ b/core/modules/filter/src/Tests/FilterCaptionTwigDebugTest.php @@ -0,0 +1,109 @@ +<?php + +/** + * @file + * Contains \Drupal\filter\Tests\FilterCaptionTwigDebugTest. + */ + +namespace Drupal\filter\Tests; + +use Drupal\Core\Render\RenderContext; +use Drupal\simpletest\WebTestBase; +use Drupal\filter\FilterPluginCollection; + +/** + * Tests the caption filter with Twig debugging on. + * + * @group filter + */ +class FilterCaptionTwigDebugTest extends WebTestBase { + + /** + * Modules to enable. + * + * @var array + */ + public static $modules = ['system', 'filter']; + + /** + * @var \Drupal\filter\Plugin\FilterInterface[] + */ + protected $filters; + + /** + * Enables Twig debugging. + */ + protected function debugOn() { + // Enable debug, rebuild the service container, and clear all caches. + $parameters = $this->container->getParameter('twig.config'); + if (!$parameters['debug']) { + $parameters['debug'] = TRUE; + $this->setContainerParameter('twig.config', $parameters); + $this->rebuildContainer(); + $this->resetAll(); + } + } + + /** + * Disables Twig debugging. + */ + protected function debugOff() { + // Disable debug, rebuild the service container, and clear all caches. + $parameters = $this->container->getParameter('twig.config'); + if ($parameters['debug']) { + $parameters['debug'] = FALSE; + $this->setContainerParameter('twig.config', $parameters); + $this->rebuildContainer(); + $this->resetAll(); + } + } + + /** + * {@inheritdoc} + */ + protected function setUp() { + parent::setUp(); + + $this->debugOn(); + + $manager = $this->container->get('plugin.manager.filter'); + $bag = new FilterPluginCollection($manager, []); + $this->filters = $bag->getAll(); + } + + /** + * {@inheritdoc} + */ + protected function tearDown() { + $this->debugOff(); + } + + /** + * Test the caption filter with Twig debugging on. + */ + function testCaptionFilter() { + /** @var \Drupal\Core\Render\RendererInterface $renderer */ + $renderer = \Drupal::service('renderer'); + $filter = $this->filters['filter_caption']; + + $test = function ($input) use ($filter, $renderer) { + return $renderer->executeInRenderContext(new RenderContext(), function () use ($input, $filter) { + return $filter->process($input, 'und'); + }); + }; + + // No data-caption attribute. + $input = '<img src="llama.jpg" />'; + $expected = $input; + $this->assertIdentical($expected, $test($input)->getProcessedText()); + + // Data-caption attribute. + $input = '<img src="llama.jpg" data-caption="Loquacious llama!" />'; + $expected = '<img src="llama.jpg" /><figcaption>Loquacious llama!</figcaption>'; + $output = $test($input); + $output = $output->getProcessedText(); + $this->assertTrue(strpos($output, $expected) !== FALSE, "\"$output\" contains \"$expected\""); + $this->assertTrue(strpos($output, '<!-- THEME HOOK: \'filter_caption\' -->') !== FALSE, 'filter_caption theme hook debug comment is present.'); + } + +} -- GitLab