function bootstrap_and_dispatch() { $phases = $this->bootstrap_init_phases(); $return = ''; $command_found = FALSE; _drush_bootstrap_output_prepare(); foreach ($phases as $phase) { if (drush_bootstrap_to_phase($phase)) { $command = drush_parse_command(); if (is_array($command)) { $command += $this->command_defaults(); // Insure that we have bootstrapped to a high enough // phase for the command prior to enforcing requirements. $bootstrap_result = drush_bootstrap_to_phase($command['bootstrap']); $this->enforce_requirement($command); if ($bootstrap_result && empty($command['bootstrap_errors'])) { $this->logger->log(LogLevel::BOOTSTRAP, dt("Found command: !command (commandfile=!commandfile)", array('!command' => $command['command'], '!commandfile' => $command['commandfile']))); $command_found = TRUE; // Dispatch the command(s). $return = drush_dispatch($command); if (drush_get_context('DRUSH_DEBUG') && !drush_get_context('DRUSH_QUIET')) { // @todo Create version independant wrapper around Drupal timers. Use it. drush_print_timers(); } break; } } } else { break; } } // TODO: If we could not find a legacy Drush command, try running a // command via the Symfony application. See also drush_main() in preflight.inc; // ultimately, the Symfony application should be called from there. if (!$command_found && isset($command)) { $container = \Drush::getContainer(); $application = $container->get('application'); $args = drush_get_arguments(); if (count($args)) { $name = $args[0]; if ($this->hasRegisteredSymfonyCommand($application, $name)) { $command_found = true; $input = drush_symfony_input(); $this->logger->log(LogLevel::BOOTSTRAP, dt("Dispatching with Symfony application as a fallback, since no native Drush command was found. (Set DRUSH_SYMFONY environment variable to skip Drush dispatch.)")); $application->run($input); } } } if (!$command_found) { // If we reach this point, command doesn't fit requirements or we have not // found either a valid or matching command. $this->report_command_error($command); } // Prevent a '1' at the end of the output. if ($return === TRUE) { $return = ''; } return $return; }
function commandfile_searchpaths($phase, $phase_max = FALSE) { if (!$phase_max) { $phase_max = $phase; } $container = \Drush::getContainer(); $discovery = $container->get('commandDiscovery'); $commandFiles = []; $searchpath = []; switch ($phase) { case DRUSH_BOOTSTRAP_DRUPAL_ROOT: $drupal_root = \Drush::bootstrapManager()->getRoot(); $searchpath[] = $drupal_root . '/../drush'; $searchpath[] = $drupal_root . '/drush'; $searchpath[] = $drupal_root . '/sites/all/drush'; $commandFiles = $discovery->discover($searchpath, '\\Drupal'); break; case DRUSH_BOOTSTRAP_DRUPAL_SITE: // If we are going to stop bootstrapping at the site, then // we will quickly add all commandfiles that we can find for // any extension associated with the site, whether it is enabled // or not. If we are, however, going to continue on to bootstrap // all the way to DRUSH_BOOTSTRAP_DRUPAL_FULL, then we will // instead wait for that phase, which will more carefully add // only those Drush commandfiles that are associated with // enabled modules. if ($phase_max < DRUSH_BOOTSTRAP_DRUPAL_FULL) { $searchpath = array_merge($searchpath, $this->contrib_modules_paths()); // Adding commandfiles located within /profiles. Try to limit to one profile for speed. Note // that Drupal allows enabling modules from a non-active profile so this logic is kinda dodgy. $cid = drush_cid_install_profile(); if ($cached = drush_cache_get($cid)) { $profile = $cached->data; $searchpath[] = "profiles/{$profile}/modules"; $searchpath[] = "profiles/{$profile}/themes"; } else { // If install_profile is not available, scan all profiles. $searchpath[] = "profiles"; $searchpath[] = "sites/all/profiles"; } $searchpath = array_merge($searchpath, $this->contrib_themes_paths()); // Drupal 8 uses the modules' services files to find commandfiles. Should we allow // redundant find-module-by-location for Drupal 8? (Maybe not.) if (drush_drupal_major_version() < 8) { $commandFiles = $discovery->discoverNamespaced($searchpath, '\\Drupal'); } } break; case DRUSH_BOOTSTRAP_DRUPAL_CONFIGURATION: // Nothing to do here anymore. Left for documentation. break; case DRUSH_BOOTSTRAP_DRUPAL_FULL: // Add enabled module paths, excluding the install profile. Since we are bootstrapped, // we can use the Drupal API. $ignored_modules = drush_get_option_list('ignored-modules', array()); $cid = drush_cid_install_profile(); if ($cached = drush_cache_get($cid)) { $ignored_modules[] = $cached->data; } foreach (array_diff(drush_module_list(), $ignored_modules) as $module) { $filepath = drupal_get_path('module', $module); if ($filepath && $filepath != '/') { $searchpath[] = $filepath; } } // Check all enabled themes including non-default and non-admin. foreach (drush_theme_list() as $key => $value) { $searchpath[] = drupal_get_path('theme', $key); } // Drupal 8 uses the modules' services files to find commandfiles. Should we allow // redundant find-module-by-location for Drupal 8? (Maybe not.) if (drush_drupal_major_version() < 8) { $commandFiles = $discovery->discoverNamespaced($searchpath, '\\Drupal'); } break; } // A little inelegant, but will do for now. drush_init_register_command_files($container, $commandFiles); return $searchpath; }
function bootstrap_drupal_full() { drush_log(dt('About to bootstrap the Drupal 8 Kernel.'), LogLevel::DEBUG); // TODO: do we need to do ob_start any longer? if (!drush_get_context('DRUSH_QUIET', FALSE)) { ob_start(); } $this->kernel->invalidateContainer(); $this->kernel->boot(); $this->kernel->prepareLegacyRequest($this->request); if (!drush_get_context('DRUSH_QUIET', FALSE)) { ob_end_clean(); } drush_log(dt('Finished bootstraping the Drupal 8 Kernel.'), LogLevel::DEBUG); parent::bootstrap_drupal_full(); // Get a list of the modules to ignore $ignored_modules = drush_get_option_list('ignored-modules', array()); // We have to get the service command list from the container, because // it is constructed in an indirect way during the container initialization. // The upshot is that the list of console commands is not available // until after $kernel->boot() is called. $container = \Drupal::getContainer(); $serviceCommandlist = $container->get('drush.service.consolecommands'); foreach ($serviceCommandlist->getCommandList() as $command) { if (!$this->commandIgnored($command, $ignored_modules)) { drush_log(dt('Add a command: !name', ['!name' => $command->getName()]), LogLevel::DEBUG); drush_add_command_to_application(\Drush::getContainer(), $command); } } // Do the same thing with the annotation commands. $serviceCommandlist = $container->get('drush.service.consolidationcommands'); foreach ($serviceCommandlist->getCommandList() as $commandhandler) { if (!$this->commandIgnored($commandhandler, $ignored_modules)) { drush_log(dt('Add a commandhandler: !name', ['!name' => get_class($commandhandler)]), LogLevel::DEBUG); drush_create_commands_from_command_instance(\Drush::getContainer(), $commandhandler); } } }