/** * Using the config item "behat_path", run composer update and bin/behat in the behat path. * * @param InputInterface $input * @param OutputInterface $output */ protected function executeBehatTests(InputInterface $input, OutputInterface $output) { $output->writeln('Running Behat Tests...'); $environment_factory = new EnvironmentFactory($this->environment, $this->app); $environment_factory->getConfig(); // 1. Look for behat.yml $behat_path = $this->environment->path . '/' . $environment_factory->config['behat_path']; $behat_yml_path = $behat_path . '/behat.yml'; if (!file_exists($behat_path)) { throw new \Exception("Path {$behat_path} not found. Check your app's .terra.yml file."); } elseif (!file_exists($behat_yml_path)) { throw new \Exception("Behat.yml file not found at {$behat_yml_path}. Check your app's .terra.yml file."); } $output->writeln('Found behat.yml file at ' . $behat_yml_path); // 2. Load it, replace necessary items, and clone it to a temporary file. $behat_yml = Yaml::parse(file_get_contents($behat_yml_path)); // Set Base URL $behat_yml['default']['extensions']['Behat\\MinkExtension']['base_url'] = "http://{$environment_factory->getHost()}:{$environment_factory->getPort()}"; $behat_yml['default']['extensions']['Drupal\\DrupalExtension']['drush']['alias'] = $environment_factory->getDrushAlias(); // If driver is drupal, add root. if ($behat_yml['default']['extensions']['Drupal\\DrupalExtension']['api_driver'] == 'drupal') { $behat_yml['default']['extensions']['Drupal\\DrupalExtension']['drupal']['root'] = $environment_factory->getDocumentRoot(); } $behat_yml_new = Yaml::dump($behat_yml, 5, 2); $behat_path_new = 'behat.terra.yml'; $fs = new Filesystem(); $fs->dumpFile($behat_path_new, $behat_yml_new); $output->writeln('Generated new behat.yml file at ' . $behat_path_new); // 3. Run `composer install` in behat_path. $output->writeln(''); $output->writeln('<fg=cyan>TERRA</> | <comment>Running: composer install</comment>'); $process = new Process('composer install', $behat_path); $process->setTimeout(NULL); $process->run(function ($type, $buffer) { if (Process::ERR === $type) { echo $buffer; } else { echo $buffer; } }); $output->writeln(''); $output->writeln('<fg=cyan>TERRA</> | <comment>Behat Tests: Start</comment>'); // 4. Run `bin/behat --colors --config=$PATH` in behat_path. // "expand:true" expands scenario outlines, making them readable. $cmd = 'bin/behat --colors --format-settings=\'{"expand": true}\' --config=' . $behat_path_new; if ($input->getOption('name')) { $cmd .= ' --name=' . $input->getOption('name'); } $output->writeln("Running: {$cmd}"); $output->writeln("in: {$behat_path}"); $output->writeln(''); $process = new Process($cmd, $behat_path); $process->setTimeout(NULL); $process->run(function ($type, $buffer) { if (Process::ERR === $type) { echo $buffer; } else { echo $buffer; } }); $output->writeln(''); if (!$process->isSuccessful()) { $output->writeln('<fg=cyan>TERRA</> | <fg=red>Test Failed</> '); return 1; } else { $output->writeln('<fg=cyan>TERRA</> | <info>Test Passed!</info> '); return 0; } }
protected function execute(InputInterface $input, OutputInterface $output) { // Ask for an app and environment. $this->getApp($input, $output); $this->getEnvironment($input, $output); // Don't continue unless we have an environment. if (empty($this->environment)) { return; } // Get Environment and Config $environment_factory = new EnvironmentFactory($this->environment, $this->app); $environment_factory->getConfig(); // Get argument override $rebuild_source_argument = $input->getOption('source'); // Check for config if (empty($environment_factory->config['rebuild_source'])) { if (empty($rebuild_source_argument)) { throw new \Exception("To run the 'environment:rebuild' command you must have 'rebuild_source: @drushalias' in your app's .terra.yml file (or specify the source drush alias with 'environment:rebuild --rebuild_source=@alias')."); } } else { $rebuild_source_config = $environment_factory->config['rebuild_source']; $output->writeln("Found <comment>rebuild_source: {$rebuild_source_config}</comment> in <fg=cyan>.terra.yml</> file..."); } // Get source and target aliases $source_alias = $rebuild_source_argument ? $rebuild_source_argument : $environment_factory->config['rebuild_source']; $target_alias = $environment_factory->getDrushAlias(); // Mention to user where the alias is coming from. if ($rebuild_source_argument) { $output->writeln("Using terra command option for source alias: <fg=cyan>{$rebuild_source_argument}</>"); } // Check that source doesn't equal target if ($source_alias == $target_alias) { throw new \Exception("You cannot use the same source and target (Source: {$source_alias} Target:{$target_alias}). Please check your config and try again."); } // Check ssh & sql access to both. $output->writeln(''); $errors = FALSE; foreach (array($source_alias, $target_alias) as $alias) { $output->writeln("Checking access to alias <fg=cyan>{$alias}</> ..."); $cmd = "drush {$alias} ssh 'echo \$SSH_CLIENT'"; // SSH Check $process = new Process($cmd); $process->setTimeout(NULL); $process->run(); if ($process->isSuccessful()) { $output->writeln("<info>SUCCESS</info> Connected to {$alias} via SSH. <comment>{$cmd}</comment>"); } else { $output->writeln("<error>FAILURE</error> Unable to connect to {$alias} via SSH. <comment>{$cmd}</comment>"); $errors = TRUE; } // SQL $cmd = "drush {$alias} sql-query 'SHOW TABLES'"; $process = new Process($cmd); $process->setTimeout(NULL); $process->run(); if ($process->isSuccessful()) { $output->writeln("<info>SUCCESS</info> Connected to {$alias} via MySQL. <comment>{$cmd}</comment>"); } else { $output->writeln("<error>FAILURE</error> Unable to connect to {$alias} via MySQL. <comment>{$cmd}</comment>"); $errors = TRUE; } $output->writeln(''); } // If errors, don't continue if ($errors) { throw new \Exception('We were unable to connect to both of your environments. Please check your config & try again.'); } // Database Sync Confirmation $helper = $this->getHelper('question'); $question = new ConfirmationQuestion("Are you sure you want to destroy <fg=red>{$target_alias}</> and replace it with data from <fg=cyan>{$source_alias}</>? [y\\N] ", false); if (!$helper->ask($input, $output, $question)) { $output->writeln('<error>Database sync Cancelled</error>'); } else { // Database Sync $cmd = "drush {$source_alias} sql-dump --gzip | gzip -cd | drush {$target_alias} sqlc"; $output->writeln(''); $output->writeln('Running...'); $output->writeln("<comment>{$cmd}</comment>"); $process = new Process($cmd); $process->setTimeout(NULL); $process->run(); if ($process->isSuccessful()) { $output->writeln("<info>SUCCESS</info> Database Copied successfully!"); } else { $output->writeln("<error>FAILURE</error> Database Copy Failed!"); } } // Files Sync Confirmation $helper = $this->getHelper('question'); $question = new ConfirmationQuestion("Copy files from <fg=cyan>{$source_alias}</> to <fg=red>{$target_alias}</>? Any existing files will be overwritten [y\\N] ", false); if (!$helper->ask($input, $output, $question)) { $output->writeln('<error>Files sync cancelled</error>'); return; } // Files Sync // Get Source Path $source_files_path = $environment_factory->runDrushCommand('vget file_public_path --format=string', $source_alias); $target_files_path = $environment_factory->runDrushCommand('vget file_public_path --format=string'); // If either variable is blank, assume default if (strpos($source_files_path, 'No matching') === 0) { $source_files_path = 'sites/default/files'; } if (strpos($target_files_path, 'No matching') === 0) { $target_files_path = 'sites/default/files'; } $default_source = "{$source_alias}:{$source_files_path}/"; $default_target = $environment_factory->getSourcePath() . '/' . $environment_factory->config['document_root'] . '/' . $target_files_path . '/'; $source_question = new Question("Source path? [{$default_source}] ", $default_source); $destination_question = new Question("Destination path? [{$default_target}] ", $default_target); $source = $helper->ask($input, $output, $source_question); $target = $helper->ask($input, $output, $destination_question); $cmd = "drush -y rsync {$source} {$target}"; $output->writeln(''); $output->writeln('Running...'); $output->writeln("<comment>{$cmd}</comment>"); $process = new Process($cmd); $process->setTimeout(NULL); $process->run(); if ($process->isSuccessful()) { $output->writeln("<info>SUCCESS</info> Files copied successfully!"); } else { $output->writeln("<error>FAILURE</error> Files did not copy successfully!"); } // Rebuild Hooks if (isset($environment_factory->config['hooks']['rebuild'])) { $output->writeln(''); $output->writeln('Running <fg=cyan>rebuild</> hooks from .terra.yml...'); $output->writeln("<comment>{$environment_factory->config['hooks']['rebuild']}</comment>"); $process = new Process($environment_factory->config['hooks']['rebuild'], $environment_factory->getSourcePath()); $process->setTimeout(NULL); $process->run(function ($type, $buffer) { if (Process::ERR === $type) { echo $buffer; } else { echo $buffer; } }); if ($process->isSuccessful()) { $output->writeln("<info>SUCCESS</info> Rebuild hooks completed successfully."); } else { $output->writeln("<error>FAILURE</error> Rebuild hooks did not complete successfully."); } $output->writeln(''); } }