ResolvedLibraryDefinitionsFilesMatchTest.php 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201
  1. <?php
  2. namespace Drupal\KernelTests\Core\Asset;
  3. use Drupal\KernelTests\KernelTestBase;
  4. /**
  5. * Tests that the asset files for all core libraries exist.
  6. *
  7. * This test also changes the active theme to each core theme to verify
  8. * the libraries after theme-level libraries-override and libraries-extend are
  9. * applied.
  10. *
  11. * @group Asset
  12. */
  13. class ResolvedLibraryDefinitionsFilesMatchTest extends KernelTestBase {
  14. /**
  15. * The theme handler.
  16. *
  17. * @var \Drupal\Core\Extension\ThemeHandlerInterface
  18. */
  19. protected $themeHandler;
  20. /**
  21. * The theme initialization.
  22. *
  23. * @var \Drupal\Core\Theme\ThemeInitializationInterface
  24. */
  25. protected $themeInitialization;
  26. /**
  27. * The theme manager.
  28. *
  29. * @var \Drupal\Core\Theme\ThemeManagerInterface
  30. */
  31. protected $themeManager;
  32. /**
  33. * The library discovery service.
  34. *
  35. * @var \Drupal\Core\Asset\LibraryDiscoveryInterface
  36. */
  37. protected $libraryDiscovery;
  38. /**
  39. * A list of all core modules.
  40. *
  41. * @var string[]
  42. */
  43. protected $allModules;
  44. /**
  45. * A list of all core themes.
  46. *
  47. * We hardcode this because test themes don't use a 'package' or 'hidden' key
  48. * so we don't have a good way of filtering to only get "real" themes.
  49. *
  50. * @var string[]
  51. */
  52. protected $allThemes = [
  53. 'bartik',
  54. 'classy',
  55. 'seven',
  56. 'stable',
  57. 'stark',
  58. ];
  59. /**
  60. * A list of libraries to skip checking, in the format extension/library_name.
  61. *
  62. * @var string[]
  63. */
  64. protected $librariesToSkip = [
  65. // Locale has a "dummy" library that does not actually exist.
  66. 'locale/translations',
  67. ];
  68. /**
  69. * A list of all paths that have been checked.
  70. *
  71. * @var array[]
  72. */
  73. protected $pathsChecked;
  74. /**
  75. * {@inheritdoc}
  76. */
  77. public static $modules = ['system'];
  78. /**
  79. * {@inheritdoc}
  80. */
  81. protected function setUp() {
  82. parent::setUp();
  83. // Install all core themes.
  84. sort($this->allThemes);
  85. $this->container->get('theme_installer')->install($this->allThemes);
  86. // Enable all core modules.
  87. $all_modules = system_rebuild_module_data();
  88. $all_modules = array_filter($all_modules, function ($module) {
  89. // Filter contrib, hidden, already enabled modules and modules in the
  90. // Testing package.
  91. if ($module->origin !== 'core' || !empty($module->info['hidden']) || $module->status == TRUE || $module->info['package'] == 'Testing') {
  92. return FALSE;
  93. }
  94. return TRUE;
  95. });
  96. $this->allModules = array_keys($all_modules);
  97. $this->allModules[] = 'system';
  98. sort($this->allModules);
  99. $this->container->get('module_installer')->install($this->allModules);
  100. $this->themeHandler = $this->container->get('theme_handler');
  101. $this->themeInitialization = $this->container->get('theme.initialization');
  102. $this->themeManager = $this->container->get('theme.manager');
  103. $this->libraryDiscovery = $this->container->get('library.discovery');
  104. }
  105. /**
  106. * Ensures that all core module and theme library files exist.
  107. */
  108. public function testCoreLibraryCompleteness() {
  109. // First verify all libraries with no active theme.
  110. $this->verifyLibraryFilesExist($this->getAllLibraries());
  111. // Then verify all libraries for each core theme. This may seem like
  112. // overkill but themes can override and extend other extensions' libraries
  113. // and these changes are only applied for the active theme.
  114. foreach ($this->allThemes as $theme) {
  115. $this->themeManager->setActiveTheme($this->themeInitialization->getActiveThemeByName($theme));
  116. $this->libraryDiscovery->clearCachedDefinitions();
  117. $this->verifyLibraryFilesExist($this->getAllLibraries());
  118. }
  119. }
  120. /**
  121. * Checks that all the library files exist.
  122. *
  123. * @param array[] $library_definitions
  124. * An array of library definitions, keyed by extension, then by library, and
  125. * so on.
  126. */
  127. protected function verifyLibraryFilesExist($library_definitions) {
  128. $root = \Drupal::root();
  129. foreach ($library_definitions as $extension => $libraries) {
  130. foreach ($libraries as $library_name => $library) {
  131. if (in_array("$extension/$library_name", $this->librariesToSkip)) {
  132. continue;
  133. }
  134. // Check that all the assets exist.
  135. foreach (['css', 'js'] as $asset_type) {
  136. foreach ($library[$asset_type] as $asset) {
  137. $file = $asset['data'];
  138. $path = $root . '/' . $file;
  139. // Only check and assert each file path once.
  140. if (!isset($this->pathsChecked[$path])) {
  141. $this->assertTrue(is_file($path), "$file file referenced from the $extension/$library_name library exists.");
  142. $this->pathsChecked[$path] = TRUE;
  143. }
  144. }
  145. }
  146. }
  147. }
  148. }
  149. /**
  150. * Gets all libraries for core and all installed modules.
  151. *
  152. * @return \Drupal\Core\Extension\Extension[]
  153. */
  154. protected function getAllLibraries() {
  155. $modules = \Drupal::moduleHandler()->getModuleList();
  156. $extensions = $modules;
  157. $module_list = array_keys($modules);
  158. sort($module_list);
  159. $this->assertEqual($this->allModules, $module_list, 'All core modules are installed.');
  160. $themes = $this->themeHandler->listInfo();
  161. $extensions += $themes;
  162. $theme_list = array_keys($themes);
  163. sort($theme_list);
  164. $this->assertEqual($this->allThemes, $theme_list, 'All core themes are installed.');
  165. $libraries['core'] = $this->libraryDiscovery->getLibrariesByExtension('core');
  166. $root = \Drupal::root();
  167. foreach ($extensions as $extension_name => $extension) {
  168. $library_file = $extension->getPath() . '/' . $extension_name . '.libraries.yml';
  169. if (is_file($root . '/' . $library_file)) {
  170. $libraries[$extension_name] = $this->libraryDiscovery->getLibrariesByExtension($extension_name);
  171. }
  172. }
  173. return $libraries;
  174. }
  175. }