diff --git a/core/lib/Drupal/Core/Extension/ThemeInstaller.php b/core/lib/Drupal/Core/Extension/ThemeInstaller.php index 99de386..f86a08c 100644 --- a/core/lib/Drupal/Core/Extension/ThemeInstaller.php +++ b/core/lib/Drupal/Core/Extension/ThemeInstaller.php @@ -56,6 +56,11 @@ class ThemeInstaller implements ThemeInstallerInterface { */ protected $logger; + /** + * @var \Drupal\Core\Extension\ModuleInstallerInterface|NULL + */ + protected $moduleInstaller; + /** * Constructs a new ThemeInstaller. @@ -82,7 +87,7 @@ class ThemeInstaller implements ThemeInstallerInterface { * @param \Drupal\Core\State\StateInterface $state * The state store. */ - public function __construct(ThemeHandlerInterface $theme_handler, ConfigFactoryInterface $config_factory, ConfigInstallerInterface $config_installer, ModuleHandlerInterface $module_handler, ConfigManagerInterface $config_manager, AssetCollectionOptimizerInterface $css_collection_optimizer, RouteBuilderInterface $route_builder, LoggerInterface $logger, StateInterface $state) { + public function __construct(ThemeHandlerInterface $theme_handler, ConfigFactoryInterface $config_factory, ConfigInstallerInterface $config_installer, ModuleHandlerInterface $module_handler, ConfigManagerInterface $config_manager, AssetCollectionOptimizerInterface $css_collection_optimizer, RouteBuilderInterface $route_builder, LoggerInterface $logger, StateInterface $state, ModuleInstallerInterface $module_installer = NULL) { $this->themeHandler = $theme_handler; $this->configFactory = $config_factory; $this->configInstaller = $config_installer; @@ -92,6 +97,17 @@ public function __construct(ThemeHandlerInterface $theme_handler, ConfigFactoryI $this->routeBuilder = $route_builder; $this->logger = $logger; $this->state = $state; + $this->moduleInstaller = $module_installer; + } + + /** + * @return \Drupal\Core\Extension\ModuleInstallerInterface + */ + protected function getModuleInstaller() { + if (!isset($this->moduleInstaller)) { + $this->moduleInstaller = \Drupal::service('module_installer'); + } + return $this->moduleInstaller; } /** @@ -118,6 +134,11 @@ public function install(array $theme_list, $install_dependencies = TRUE) { } while (list($theme) = each($theme_list)) { + $module_dependencies = array_diff_key($theme_data[$theme]->requires, $theme_data); + $theme_dependencies = array_diff_key($theme_data[$theme]->requires, $module_dependencies); + $this->getModuleInstaller()->install(array_keys($module_dependencies)); + $theme_data[$theme]->requires = $theme_dependencies; + // Add dependencies to the list. The new themes will be processed as // the while loop continues. foreach (array_keys($theme_data[$theme]->requires) as $dependency) { diff --git a/core/modules/system/system.admin.inc b/core/modules/system/system.admin.inc index f9c49c7..2b4eb8f 100644 --- a/core/modules/system/system.admin.inc +++ b/core/modules/system/system.admin.inc @@ -371,6 +371,8 @@ function template_preprocess_system_themes_page(&$variables) { $current_theme['incompatible'] = t('This theme requires the theme engine @theme_engine to operate correctly.', array('@theme_engine' => $theme->info['engine'])); } + $current_theme['requires'] = $theme->requires; + // Build operation links. $current_theme['operations'] = array( '#theme' => 'links', diff --git a/core/modules/system/templates/system-themes-page.html.twig b/core/modules/system/templates/system-themes-page.html.twig index 6e65d76..02a0a82 100644 --- a/core/modules/system/templates/system-themes-page.html.twig +++ b/core/modules/system/templates/system-themes-page.html.twig @@ -66,6 +66,9 @@ {% if theme.incompatible %}
{{ theme.incompatible }}
{% else %} + {% if theme.requires %} + Module dependencies: {{ theme.requires | keys | safe_join(', ')}} + {% endif %} {{ theme.operations }} {% endif %} diff --git a/core/modules/system/tests/themes/test_theme_module_dependency/test_theme_dependency/src/Service.php b/core/modules/system/tests/themes/test_theme_module_dependency/test_theme_dependency/src/Service.php new file mode 100644 index 0000000..6313712 --- /dev/null +++ b/core/modules/system/tests/themes/test_theme_module_dependency/test_theme_dependency/src/Service.php @@ -0,0 +1,12 @@ +assertFalse(isset($system_list[$name]->info['regions']['test_region'])); } + public function testThemeWithModuleDependency() { + $this->assertFalse($this->moduleHandler()->moduleExists('test_theme_dependency')); + $this->themeInstaller()->install(['test_theme_module_dependency']); + $this->assertTrue($this->moduleHandler()->moduleExists('test_theme_dependency')); + + $service = \Drupal::service('test_theme_dependency.service'); + $this->assertInstanceOf(Service::class, $service); + } + /** * Returns the theme handler service. * diff --git a/core/themes/stable/templates/admin/system-themes-page.html.twig b/core/themes/stable/templates/admin/system-themes-page.html.twig index 5a23f1a..333278f 100644 --- a/core/themes/stable/templates/admin/system-themes-page.html.twig +++ b/core/themes/stable/templates/admin/system-themes-page.html.twig @@ -64,6 +64,9 @@ {% if theme.incompatible %}
{{ theme.incompatible }}
{% else %} + {% if theme.requires %} + Module dependencies: {{ theme.requires | keys | safe_join(', ')}} + {% endif %} {{ theme.operations }} {% endif %}