diff --git a/src/Drupal/DrupalKernel.php b/src/Drupal/DrupalKernel.php index 31c195fef6..3b2548d3f5 100644 --- a/src/Drupal/DrupalKernel.php +++ b/src/Drupal/DrupalKernel.php @@ -1,6 +1,7 @@ getCachedContainerDefinition(); if ($this->shouldDrushInvalidateContainer()) { + // Normally when the container is being rebuilt, the existing + // container is still available for use until the newly built one + // replaces it. Certain contrib modules rely on services (like State + // or the config factory) being available for things like defining + // event subscriptions. + // @see https://github.com/drush-ops/drush/issues/3123 + if (isset($container_definition)) { + $class = Settings::get('container_base_class', '\Drupal\Core\DependencyInjection\Container'); + $container = new $class($container_definition); + $this->attachSynthetic($container); + \Drupal::setContainer($container); + } + $this->invalidateContainer(); } return parent::initializeContainer(); diff --git a/tests/containerTest.php b/tests/containerTest.php new file mode 100644 index 0000000000..318ffde7c4 --- /dev/null +++ b/tests/containerTest.php @@ -0,0 +1,63 @@ +setUpDrupal(1, TRUE); + $root = $this->webroot(); + $options = array( + 'root' => $root, + 'uri' => $this->getUri(), + 'yes' => NULL, + ); + + // Copy the 'woot' module over to the Drupal site we just set up. + $this->setupModulesForTests($root); + + // Enable our module. + $this->drush('pm-enable', ['woot'], $options); + + // Set up for a config import with just one small piece. + $this->drush('config-export', array(), $options); + $this->drush('config-set', array('system.site', 'name', 'config_test'), $options); + + // Trigger the container rebuild we need. + $this->drush('cr', [], $options); + $this->drush('cron', [], $options); + + // If the event was registered successfully, then upon a config import, we + // should get the error message. + $this->drush('config-import', [], $options, NULL, NULL, CommandUnishTestCase::EXIT_ERROR); + $this->assertContains("woot config error", $this->getErrorOutput(), 'Event was successfully registered.'); + } + + /** + * Sets up the woot module for the test. + * + * @param string $root + * The web root. + */ + public function setupModulesForTests($root) { + $wootModule = Path::join(__DIR__, '/resources/modules/d8/woot'); + // We install into Unish so that we aren't cleaned up. That causes + // container to go invalid after tearDownAfterClass(). + $targetDir = Path::join($root, 'modules/unish/woot'); + $this->mkdir($targetDir); + $this->recursive_copy($wootModule, $targetDir); + } + +} diff --git a/tests/resources/modules/d8/woot/src/EventSubscriber/ConfigSubscriber.php b/tests/resources/modules/d8/woot/src/EventSubscriber/ConfigSubscriber.php new file mode 100644 index 0000000000..7cb5ff15ff --- /dev/null +++ b/tests/resources/modules/d8/woot/src/EventSubscriber/ConfigSubscriber.php @@ -0,0 +1,40 @@ +getConfigImporter(); + $importer->logError($this->t('woot config error')); + } + +} diff --git a/tests/resources/modules/d8/woot/woot.services.yml b/tests/resources/modules/d8/woot/woot.services.yml new file mode 100644 index 0000000000..37ccc34fef --- /dev/null +++ b/tests/resources/modules/d8/woot/woot.services.yml @@ -0,0 +1,5 @@ +services: + config.config_subscriber: + class: Drupal\woot\EventSubscriber\ConfigSubscriber + tags: + - { name: event_subscriber }