ckeditor5-1.0.x-dev/tests/src/Kernel/CKEditor5PluginManagerTest.php

tests/src/Kernel/CKEditor5PluginManagerTest.php
<?php

namespace Drupal\Tests\ckeditor5\Kernel;

use Drupal\editor\Entity\Editor;
use Drupal\KernelTests\KernelTestBase;
use Drupal\filter\Entity\FilterFormat;
use Symfony\Component\Yaml\Yaml;

// cspell:ignore layercake everyblock justblockquote

/**
 * Tests different ways of enabling CKEditor 5 plugins.
 *
 * @group ckeditor5
 */
class CKEditor5PluginManagerTest extends KernelTestBase {

  /**
   * {@inheritdoc}
   */
  protected static $modules = [
    'system',
    'user',
    'filter',
    'editor',
    'ckeditor5',
    'media',
  ];

  /**
   * The manager for "CKEditor 5 plugin" plugins.
   *
   * @var \Drupal\Component\Plugin\PluginManagerInterface
   */
  protected $manager;

  /**
   * {@inheritdoc}
   */
  protected function setUp(): void {
    parent::setUp();

    FilterFormat::create(
      Yaml::parseFile('core/profiles/standard/config/install/filter.format.basic_html.yml')
    )->save();
    Editor::create([
      'format' => 'basic_html',
      'editor' => 'ckeditor5',
    ])->save();
    FilterFormat::create(
      Yaml::parseFile('core/profiles/standard/config/install/filter.format.full_html.yml')
    )->save();
    Editor::create([
      'format' => 'full_html',
      'editor' => 'ckeditor5',
    ])->save();
    $this->manager = $this->container->get('plugin.manager.ckeditor5.plugin');
  }

  /**
   * Tests the enabling of plugins.
   */
  public function testEnabledPlugins() {
    $editor = Editor::load('basic_html');

    // Case 1: no extra CKEditor 5 plugins.
    $definitions = array_keys($this->manager->getEnabledDefinitions($editor));
    $default_plugins = [
      'ckeditor5.bold',
      'ckeditor5.emphasis',
      'ckeditor5.essentials',
      'ckeditor5.paragraph',
      'ckeditor5heading',
    ];
    $this->assertSame($default_plugins, $definitions, 'No CKEditor 5 plugins found besides the built-in ones.');
    $default_libraries = [
      'ckeditor5/ckeditor5.basic',
      'ckeditor5/ckeditor5.internal',
      'ckeditor5/drupal.ckeditor5',
      'ckeditor5/drupal.ckeditor5.emphasis',
    ];
    $this->assertSame($default_libraries, $this->manager->getEnabledLibraries($editor));

    // Enable the CKEditor 5 Test module, which has the layercake plugin and
    // clear the editor manager's static cache so that it is picked up.
    $this->enableModules(['ckeditor5_test']);
    $this->manager = $this->container->get('plugin.manager.ckeditor5.plugin');
    $this->manager->clearCachedDefinitions();

    // Case 2: The CKEditor 5 layercake plugin is available and library should
    // NOT be loaded if its toolbar items are not enabled.
    $this->assertSame($default_plugins, array_keys($this->manager->getEnabledDefinitions($editor)));
    $this->assertSame($default_libraries, $this->manager->getEnabledLibraries($editor));

    // Case 3: The CKEditor 5 layercake plugin is available and library should
    // be loaded without having to enable plugins.
    $settings = $editor->getSettings();
    $settings['toolbar']['items'][] = 'simpleBox';
    $editor->setSettings($settings);
    $plugin_ids = array_keys($this->manager->getEnabledDefinitions($editor));
    $default_plugins_with_layercake = array_merge($default_plugins, ['ckeditor5_test.layercake']);

    // Sort on plugin id.
    asort($default_plugins_with_layercake);
    $this->assertSame(array_values($default_plugins_with_layercake), $plugin_ids);
    $this->assertSame(array_merge($default_libraries, [
      'ckeditor5_test/layercake',
    ]), $this->manager->getEnabledLibraries($editor));

    // Enable media embed filter which the CKEditor 5 media plugin requires.
    $editor->getFilterFormat()->setFilterConfig('media_embed', ['status' => TRUE])->save();

    // Case 4: The CKEditor 5 media plugin should be enabled and the library
    // should be available now that the media_embed is enabled.
    $plugin_ids = array_keys($this->manager->getEnabledDefinitions($editor));
    $expected_plugins = array_merge($default_plugins, [
      'ckeditor5_test.layercake',
      'ckeditor5.media',
    ]);
    sort($expected_plugins);
    $this->assertSame($expected_plugins, $plugin_ids);
    $this->assertSame(array_merge($default_libraries, [
      'ckeditor5/drupal.ckeditor5.media',
      'ckeditor5_test/layercake',
    ]), $this->manager->getEnabledLibraries($editor));

    // Case 5: GHS is only enabled for Full HTML (or any other text format that
    // has no TYPE_HTML_RESTRICTOR filters).
    $editor = Editor::load('full_html');
    $definitions = array_keys($this->manager->getEnabledDefinitions($editor));
    $default_plugins = [
      'ckeditor5.bold',
      'ckeditor5.emphasis',
      'ckeditor5.essentials',
      'ckeditor5.htmlSupport',
      'ckeditor5.paragraph',
      'ckeditor5heading',
    ];
    $this->assertSame($default_plugins, $definitions, 'No CKEditor 5 plugins found besides the built-in ones.');
    $default_libraries = [
      'ckeditor5/ckeditor5.basic',
      'ckeditor5/ckeditor5.htmlSupport',
      'ckeditor5/ckeditor5.internal',
      'ckeditor5/drupal.ckeditor5',
      'ckeditor5/drupal.ckeditor5.emphasis',
    ];
    $this->assertSame($default_libraries, $this->manager->getEnabledLibraries($editor));
  }

  /**
   * Tests the parsing of CKEditor 5 plugin element config.
   *
   * @param string[] $plugins
   *   The plugins to parse the elements list from.
   * @param array $expected_elements
   *   An array of expected allowed elements an attributes in the structure
   *   used by filter_html.
   * @param string $expected_readable_string
   *   The expected allowed tags and attributes as a string, typically used
   *   in the filter_html "Allowed tags" field.
   *
   * @covers \Drupal\ckeditor5\Plugin\CKEditor5PluginManager::getProvidedElements
   * @covers \Drupal\ckeditor5\Plugin\CKEditor5PluginManager::getReadableElements
   * @dataProvider providerTestProvidedElements
   */
  public function testProvidedElements(array $plugins, array $expected_elements, string $expected_readable_string) {
    $this->enableModules(['ckeditor5_plugin_elements_test']);

    $provided_elements = $this->manager->getProvidedElements($plugins);
    $this->assertSame($expected_elements, $provided_elements);
    $readable_string = $this->manager->getReadableElements($provided_elements);
    $this->assertSame($expected_readable_string, $readable_string);
  }

  /**
   * Provides uses cases enabling different elements and the expected results.
   */
  public function providerTestProvidedElements() : array {
    $text_align_classes = [
      'text-align-left' => TRUE,
      'text-align-center' => TRUE,
      'text-align-right' => TRUE,
      'text-align-justify' => TRUE,
    ];

    return [
      'language' => [
        'plugins' => ['language'],
        'expected_elements' => [
          'span' => [
            'lang' => TRUE,
            'dir' => TRUE,
          ],
        ],
        'expected_readable_string' => '<span lang dir>',
      ],
      'alignment and heading' => [
        'plugins' => [
          'ckeditor5.alignment',
          'ckeditor5heading',
          'ckeditor5.paragraph',
        ],
        'expected_elements' => [
          'p' => [
            'class' => $text_align_classes,
          ],
          'br' => FALSE,
          'h1' => [
            'class' => $text_align_classes,
          ],
          'h2' => [
            'class' => $text_align_classes,
          ],
          'h3' => [
            'class' => $text_align_classes,
          ],
          'h4' => [
            'class' => $text_align_classes,
          ],
          'h5' => [
            'class' => $text_align_classes,
          ],
          'h6' => [
            'class' => $text_align_classes,
          ],
        ],
        'expected_readable_string' => '<p class="text-align-left text-align-center text-align-right text-align-justify"> <br> <h1 class="text-align-left text-align-center text-align-right text-align-justify"> <h2 class="text-align-left text-align-center text-align-right text-align-justify"> <h3 class="text-align-left text-align-center text-align-right text-align-justify"> <h4 class="text-align-left text-align-center text-align-right text-align-justify"> <h5 class="text-align-left text-align-center text-align-right text-align-justify"> <h6 class="text-align-left text-align-center text-align-right text-align-justify">',
      ],
      'alignment and heading, but all class values allowed for headings' => [
        'plugins' => [
          'ckeditor5.alignment',
          'ckeditor5heading',
          'ckeditor5.paragraph',
          'headings.use.class.any.value',
        ],
        'expected_elements' => [
          'p' => [
            'class' => $text_align_classes,
          ],
          'br' => FALSE,
          'h1' => [
            'class' => TRUE,
          ],
          'h2' => [
            'class' => TRUE,
          ],
          'h3' => [
            'class' => TRUE,
          ],
          'h4' => [
            'class' => TRUE,
          ],
          'h5' => [
            'class' => TRUE,
          ],
          'h6' => [
            'class' => TRUE,
          ],
        ],
        'expected_readable_string' => '<p class="text-align-left text-align-center text-align-right text-align-justify"> <br> <h1 class> <h2 class> <h3 class> <h4 class> <h5 class> <h6 class>',
      ],
      'blockquote combo' => [
        'plugins' => [
          'blockquote.combo',
          'ckeditor5.paragraph',
        ],
        'expected_elements' => [
          'p' => [
            'data-everyblock' => TRUE,
          ],
          'br' => FALSE,
          'blockquote' => [
            'data-justblockquote' => TRUE,
            'data-everyblock' => TRUE,
          ],
        ],
        'expected_readable_string' => '<p data-everyblock> <br> <blockquote data-justblockquote data-everyblock>',
      ],
      'headings plus headings with attributes' => [
        'plugins' => [
          'headings.with.other.attributes',
          'ckeditor5heading',
        ],
        'expected_elements' => [
          'h1' => [
            'data-just-h1' => TRUE,
          ],
          'h2' => [
            'class' => [
              'additional-allowed-class' => TRUE,
            ],
          ],
          'h3' => [
            'data-just-h3' => TRUE,
            'data-just-h3-limited' => [
              'i-am-the-only-allowed-value' => TRUE,
            ],
          ],
          'h4' => FALSE,
          'h5' => [
            'data-just-h5-limited' => [
              'first-allowed-value' => TRUE,
              'second-allowed-value' => TRUE,
            ],
          ],
          'h6' => FALSE,
        ],
        'expected_readable_string' => '<h1 data-just-h1> <h2 class="additional-allowed-class"> <h3 data-just-h3 data-just-h3-limited="i-am-the-only-allowed-value"> <h4> <h5 data-just-h5-limited="first-allowed-value second-allowed-value"> <h6>',
      ],
      'headings plus headings with attributes and alignment' => [
        'plugins' => [
          'headings.with.other.attributes',
          'ckeditor5heading',
          'ckeditor5.alignment',
        ],
        'expected_elements' => [
          'h1' => [
            'data-just-h1' => TRUE,
            'class' => $text_align_classes,
          ],
          'h2' => [
            'class' => ['additional-allowed-class' => TRUE] + $text_align_classes,
          ],
          'h3' => [
            'data-just-h3' => TRUE,
            'data-just-h3-limited' => [
              'i-am-the-only-allowed-value' => TRUE,
            ],
            'class' => $text_align_classes,
          ],
          'h4' => [
            'class' => $text_align_classes,
          ],
          'h5' => [
            'data-just-h5-limited' => [
              'first-allowed-value' => TRUE,
              'second-allowed-value' => TRUE,
            ],
            'class' => $text_align_classes,
          ],
          'h6' => [
            'class' => $text_align_classes,
          ],
        ],
        'expected_readable_string' => '<h1 data-just-h1 class="text-align-left text-align-center text-align-right text-align-justify"> <h2 class="additional-allowed-class text-align-left text-align-center text-align-right text-align-justify"> <h3 data-just-h3 data-just-h3-limited="i-am-the-only-allowed-value" class="text-align-left text-align-center text-align-right text-align-justify"> <h4 class="text-align-left text-align-center text-align-right text-align-justify"> <h5 data-just-h5-limited="first-allowed-value second-allowed-value" class="text-align-left text-align-center text-align-right text-align-justify"> <h6 class="text-align-left text-align-center text-align-right text-align-justify">',
      ],
    ];
  }

}

Главная | Обратная связь

drupal hosting | друпал хостинг | it patrol .inc