Skip to content

Commit 72aae3e

Browse files
authored
Avoid side effects in FeatureContext file (#292)
1 parent 500516c commit 72aae3e

File tree

2 files changed

+80
-86
lines changed

2 files changed

+80
-86
lines changed

bin/run-behat-tests

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -120,4 +120,4 @@ if [[ "${WP_CLI_TEST_COVERAGE}" == "true" ]] && vendor/bin/behat --help 2>/dev/n
120120
fi
121121

122122
# Run the functional tests.
123-
vendor/bin/behat --format progress "$BEHAT_TAGS" --strict "${BEHAT_EXTRA_ARGS[@]}" "$@"
123+
vendor/bin/behat --snippets-for="WP_CLI\Tests\Context\FeatureContext" --format progress "$BEHAT_TAGS" --strict "${BEHAT_EXTRA_ARGS[@]}" "$@"

src/Context/FeatureContext.php

Lines changed: 79 additions & 85 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22

33
namespace WP_CLI\Tests\Context;
44

5-
use Behat\Behat\Context\SnippetAcceptingContext;
5+
use Behat\Behat\Context\Context;
66
use Behat\Behat\EventDispatcher\Event\OutlineTested;
77
use Behat\Behat\Hook\Scope\AfterScenarioScope;
88
use Behat\Behat\Hook\Scope\BeforeScenarioScope;
@@ -13,15 +13,13 @@
1313
use Behat\Behat\Hook\Scope\AfterFeatureScope;
1414
use Behat\Behat\Hook\Scope\BeforeFeatureScope;
1515
use Behat\Behat\Hook\Scope\BeforeStepScope;
16-
use Behat\Testwork\Hook\Scope\HookScope;
1716
use SebastianBergmann\CodeCoverage\Report\Clover;
1817
use SebastianBergmann\CodeCoverage\Driver\Selector;
1918
use SebastianBergmann\CodeCoverage\Driver\Xdebug;
2019
use SebastianBergmann\CodeCoverage\Filter;
2120
use SebastianBergmann\CodeCoverage\CodeCoverage;
2221
use SebastianBergmann\Environment\Runtime;
2322
use RuntimeException;
24-
use WP_CLI;
2523
use DirectoryIterator;
2624
use WP_CLI\Process;
2725
use WP_CLI\ProcessRun;
@@ -30,10 +28,8 @@
3028

3129
/**
3230
* Features context.
33-
*
34-
* @phpstan-ignore class.implementsDeprecatedInterface
3531
*/
36-
class FeatureContext implements SnippetAcceptingContext {
32+
class FeatureContext implements Context {
3733

3834
use GivenStepDefinitions;
3935
use ThenStepDefinitions;
@@ -282,9 +278,6 @@ private static function running_with_code_coverage() {
282278
return \in_array( $with_code_coverage, [ 'true', '1' ], true );
283279
}
284280

285-
/**
286-
* @AfterSuite
287-
*/
288281
public static function merge_coverage_reports(): void {
289282
if ( ! self::running_with_code_coverage() ) {
290283
return;
@@ -430,14 +423,14 @@ private static function get_process_env_variables(): array {
430423

431424
// Ensure we're using the expected `wp` binary.
432425
$bin_path = self::get_bin_path();
433-
wp_cli_behat_env_debug( "WP-CLI binary path: {$bin_path}" );
426+
self::debug( "WP-CLI binary path: {$bin_path}" );
434427

435428
if ( ! file_exists( "{$bin_path}/wp" ) ) {
436-
wp_cli_behat_env_debug( "WARNING: No file named 'wp' found in the provided/detected binary path." );
429+
self::debug( "WARNING: No file named 'wp' found in the provided/detected binary path." );
437430
}
438431

439432
if ( ! is_executable( "{$bin_path}/wp" ) ) {
440-
wp_cli_behat_env_debug( "WARNING: File named 'wp' found in the provided/detected binary path is not executable." );
433+
self::debug( "WARNING: File named 'wp' found in the provided/detected binary path is not executable." );
441434
}
442435

443436
$path_separator = Utils\is_windows() ? ';' : ':';
@@ -502,9 +495,9 @@ private static function get_process_env_variables(): array {
502495
}
503496

504497
// Dump environment for debugging purposes, but before adding the GitHub token.
505-
wp_cli_behat_env_debug( 'Environment:' );
498+
self::debug( 'Environment:' );
506499
foreach ( $env as $key => $value ) {
507-
wp_cli_behat_env_debug( " [{$key}] => {$value}" );
500+
self::debug( " [{$key}] => {$value}" );
508501
}
509502

510503
$github_token = getenv( 'GITHUB_TOKEN' );
@@ -651,6 +644,8 @@ private static function cache_wp_files( $version = '' ): void {
651644
* @BeforeSuite
652645
*/
653646
public static function prepare( BeforeSuiteScope $scope ): void {
647+
self::bootstrap_feature_context();
648+
654649
// Test performance statistics - useful for detecting slow tests.
655650
self::$log_run_times = getenv( 'WP_CLI_TEST_LOG_RUN_TIMES' );
656651
if ( false !== self::$log_run_times ) {
@@ -687,6 +682,8 @@ public static function afterSuite( AfterSuiteScope $scope ): void {
687682
if ( self::$log_run_times ) {
688683
self::log_run_times_after_suite( $scope );
689684
}
685+
686+
self::merge_coverage_reports();
690687
}
691688

692689
/**
@@ -866,6 +863,74 @@ public function __construct() {
866863
$this->set_cache_dir();
867864
}
868865

866+
/**
867+
* @param string $message
868+
*/
869+
protected static function debug( $message ): void { // phpcs:ignore Universal.Files.SeparateFunctionsFromOO.Mixed
870+
if ( ! getenv( 'WP_CLI_TEST_DEBUG_BEHAT_ENV' ) ) {
871+
return;
872+
}
873+
874+
echo "{$message}\n";
875+
}
876+
877+
/**
878+
* Load required support files as needed before heading into the Behat context.
879+
*/
880+
protected static function bootstrap_feature_context(): void {
881+
$vendor_folder = self::get_vendor_dir();
882+
self::debug( "Vendor folder location: {$vendor_folder}" );
883+
884+
// Didn't manage to detect a valid vendor folder.
885+
if ( empty( $vendor_folder ) ) {
886+
return;
887+
}
888+
889+
// We assume the vendor folder is located in the project root folder.
890+
$project_folder = dirname( $vendor_folder );
891+
892+
$framework_folder = self::get_framework_dir();
893+
self::debug( "Framework folder location: {$framework_folder}" );
894+
895+
// Load helper functionality that is needed for the tests.
896+
require_once "{$framework_folder}/php/utils.php";
897+
require_once "{$framework_folder}/php/WP_CLI/Process.php";
898+
require_once "{$framework_folder}/php/WP_CLI/ProcessRun.php";
899+
900+
// Manually load Composer file includes by generating a config with require:
901+
// statements for each file.
902+
$project_composer = "{$project_folder}/composer.json";
903+
if ( ! file_exists( $project_composer ) ) {
904+
return;
905+
}
906+
907+
$composer = json_decode( file_get_contents( $project_composer ) );
908+
if ( empty( $composer->autoload->files ) ) {
909+
return;
910+
}
911+
912+
$contents = "require:\n";
913+
foreach ( $composer->autoload->files as $file ) {
914+
$contents .= " - {$project_folder}/{$file}\n";
915+
}
916+
917+
$temp_folder = sys_get_temp_dir() . '/wp-cli-package-test';
918+
if (
919+
! is_dir( $temp_folder )
920+
&& ! mkdir( $temp_folder )
921+
&& ! is_dir( $temp_folder )
922+
) {
923+
return;
924+
}
925+
926+
$project_config = "{$temp_folder}/config.yml";
927+
file_put_contents( $project_config, $contents );
928+
putenv( 'WP_CLI_CONFIG_PATH=' . $project_config );
929+
930+
self::debug( "Project config file location: {$project_config}" );
931+
self::debug( "Project config:\n{$contents}" );
932+
}
933+
869934
/**
870935
* Replace standard {VARIABLE_NAME} variables and the special {INVOKE_WP_CLI_WITH_PHP_ARGS-args} and {WP_VERSION-version-latest} variables.
871936
* Note that standard variable names can only contain uppercase letters, digits and underscores and cannot begin with a digit.
@@ -1766,74 +1831,3 @@ private static function log_proc_method_run_time( $key, $start_time ): void {
17661831
++self::$proc_method_run_times[ $key ][1];
17671832
}
17681833
}
1769-
1770-
1771-
/**
1772-
* @param string $message
1773-
*/
1774-
function wp_cli_behat_env_debug( $message ): void { // phpcs:ignore Universal.Files.SeparateFunctionsFromOO.Mixed
1775-
if ( ! getenv( 'WP_CLI_TEST_DEBUG_BEHAT_ENV' ) ) {
1776-
return;
1777-
}
1778-
1779-
echo "{$message}\n";
1780-
}
1781-
1782-
/**
1783-
* Load required support files as needed before heading into the Behat context.
1784-
*/
1785-
function wpcli_bootstrap_behat_feature_context(): void {
1786-
$vendor_folder = FeatureContext::get_vendor_dir();
1787-
wp_cli_behat_env_debug( "Vendor folder location: {$vendor_folder}" );
1788-
1789-
// Didn't manage to detect a valid vendor folder.
1790-
if ( empty( $vendor_folder ) ) {
1791-
return;
1792-
}
1793-
1794-
// We assume the vendor folder is located in the project root folder.
1795-
$project_folder = dirname( $vendor_folder );
1796-
1797-
$framework_folder = FeatureContext::get_framework_dir();
1798-
wp_cli_behat_env_debug( "Framework folder location: {$framework_folder}" );
1799-
1800-
// Load helper functionality that is needed for the tests.
1801-
require_once "{$framework_folder}/php/utils.php";
1802-
require_once "{$framework_folder}/php/WP_CLI/Process.php";
1803-
require_once "{$framework_folder}/php/WP_CLI/ProcessRun.php";
1804-
1805-
// Manually load Composer file includes by generating a config with require:
1806-
// statements for each file.
1807-
$project_composer = "{$project_folder}/composer.json";
1808-
if ( ! file_exists( $project_composer ) ) {
1809-
return;
1810-
}
1811-
1812-
$composer = json_decode( file_get_contents( $project_composer ) );
1813-
if ( empty( $composer->autoload->files ) ) {
1814-
return;
1815-
}
1816-
1817-
$contents = "require:\n";
1818-
foreach ( $composer->autoload->files as $file ) {
1819-
$contents .= " - {$project_folder}/{$file}\n";
1820-
}
1821-
1822-
$temp_folder = sys_get_temp_dir() . '/wp-cli-package-test';
1823-
if (
1824-
! is_dir( $temp_folder )
1825-
&& ! mkdir( $temp_folder )
1826-
&& ! is_dir( $temp_folder )
1827-
) {
1828-
return;
1829-
}
1830-
1831-
$project_config = "{$temp_folder}/config.yml";
1832-
file_put_contents( $project_config, $contents );
1833-
putenv( 'WP_CLI_CONFIG_PATH=' . $project_config );
1834-
1835-
wp_cli_behat_env_debug( "Project config file location: {$project_config}" );
1836-
wp_cli_behat_env_debug( "Project config:\n{$contents}" );
1837-
}
1838-
1839-
wpcli_bootstrap_behat_feature_context();

0 commit comments

Comments
 (0)