Repository: Behat/Behat (php)

Issue:
Potential type inconsistency error
  In the version 3.21.0 of this package the class \Behat\Testwork\PathOptions\Printer\ConfigurablePathPrinter expects an string in $basePath parameter of the constructor, but the \Behat\Testwork\Exception\ExceptionPresenter class passes null when this `basePath` is not specified. An empty string could be passed instead.
Error with PHPStorm feature runner
After upgrading from Behat 3.20.0 to 3.21.0 I get this error while running features from PHPStorm runner:

```
Fatal error: Uncaught TypeError: Behat\Testwork\PathOptions\Printer\ConfigurablePathPrinter::__construct(): Argument #1 ($basePath) must be of type string, null given, called in /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/Exception/ExceptionPresenter.php on line 46 and defined in /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/PathOptions/Printer/ConfigurablePathPrinter.php:17
Stack trace:
#0 /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/Exception/ExceptionPresenter.php(46): Behat\Testwork\PathOptions\Printer\ConfigurablePathPrinter->__construct(NULL, false)
#1 /opt/.phpstorm_helpers/behat.php(289): Behat\Testwork\Exception\ExceptionPresenter->__construct(NULL, 1)
#2 /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/Output/OutputManager.php(108): PhpStormBehatFormatter->__construct()
#3 /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/Output/Cli/OutputController.php(107): Behat\Testwork\Output\OutputManager->enableFormatter('PhpStormBehatFo...')
#4 /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/Output/Cli/OutputController.php(93): Behat\Testwork\Output\Cli\OutputController->enableFormatters(Array)
#5 /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/Output/Cli/OutputController.php(79): Behat\Testwork\Output\Cli\OutputController->configureFormatters(Array, Object(Symfony\Component\Console\Input\ArgvInput), Object(Symfony\Component\Console\Output\ConsoleOutput))
#6 /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/Cli/Command.php(63): Behat\Testwork\Output\Cli\OutputController->execute(Object(Symfony\Component\Console\Input\ArgvInput), Object(Symfony\Component\Console\Output\ConsoleOutput))
#7 /var/www/symfony/vendor/symfony/console/Command/Command.php(279): Behat\Testwork\Cli\Command->execute(Object(Symfony\Component\Console\Input\ArgvInput), Object(Symfony\Component\Console\Output\ConsoleOutput))
#8 /var/www/symfony/vendor/symfony/console/Application.php(1076): Symfony\Component\Console\Command\Command->run(Object(Symfony\Component\Console\Input\ArgvInput), Object(Symfony\Component\Console\Output\ConsoleOutput))
#9 /var/www/symfony/vendor/symfony/console/Application.php(342): Symfony\Component\Console\Application->doRunCommand(Object(Behat\Testwork\Cli\Command), Object(Symfony\Component\Console\Input\ArgvInput), Object(Symfony\Component\Console\Output\ConsoleOutput))
#10 /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/Cli/Application.php(141): Symfony\Component\Console\Application->doRun(Object(Symfony\Component\Console\Input\ArgvInput), Object(Symfony\Component\Console\Output\ConsoleOutput))
#11 /var/www/symfony/vendor/symfony/console/Application.php(193): Behat\Testwork\Cli\Application->doRun(Object(Symfony\Component\Console\Input\ArgvInput), Object(Symfony\Component\Console\Output\ConsoleOutput))
#12 /opt/.phpstorm_helpers/behat.php(580): Symfony\Component\Console\Application->run()
#13 {main}
  thrown in /var/www/symfony/vendor/behat/behat/src/Behat/Testwork/PathOptions/Printer/ConfigurablePathPrinter.php on line 17
```

OS: Windows 11 Pro
PHP: 8.4.2
PHPStorm: 2024.3.5

Pull request description:
fix: ExceptionPresenter was causing a TypeError with null $basePath
As reported in #1630 and #1629, we missed that the ExceptionPresenter can be validly created with a null $basePath but it is not valid to pass this to the new ConfigurablePathPrinter. Although Behat never does this, third-parties do.

The old behaviour in that case was that the ExceptionPresenter would just print absolute paths.

We can achieve the same thing by setting the correct value for printAbsolutePaths when we create the ConfigurablePathPrinter. We can then just cast the $basePath to an empty string as this will be ignored if we're printing absolute paths.

fixes #1630 
fixes #1629 

Patch:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index b8056210..6a41784b 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -4,6 +4,12 @@ All notable changes to this project will be documented in this file.
 The format is based on [Keep a Changelog](http://keepachangelog.com/)
 and this project adheres to [Semantic Versioning](http://semver.org/).
 
+## [3.21.1] - 2025-04-22
+
+### Fixed
+
+* ExceptionPresenter was causing a TypeError when constructed with a null $basePath by @acoulton in [#1631](https://github.com/Behat/Behat/pull/1631)
+
 ## [3.21.0] - 2025-04-18
 
 ### Fixed
@@ -1241,6 +1247,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
 ### Changed
   * Initial release
 
+[3.21.1]: https://github.com/Behat/Behat/compare/v3.21.0...v3.21.1
+[3.21.0]: https://github.com/Behat/Behat/compare/v3.20.0...v3.21.0
 [3.20.0]: https://github.com/Behat/Behat/compare/v3.19.0...v3.20.0
 [3.19.0]: https://github.com/Behat/Behat/compare/v3.18.1...v3.19.0
 [3.18.1]: https://github.com/Behat/Behat/compare/v3.18.0...v3.18.1


Test patch:
diff --git a/src/Behat/Testwork/Exception/ExceptionPresenter.php b/src/Behat/Testwork/Exception/ExceptionPresenter.php
index eb7e4884..697b0080 100644
--- a/src/Behat/Testwork/Exception/ExceptionPresenter.php
+++ b/src/Behat/Testwork/Exception/ExceptionPresenter.php
@@ -35,7 +35,7 @@ final class ExceptionPresenter
     /**
      * Initializes presenter.
      *
-     * @param string  $basePath deprecated, will be removed in next major version
+     * @param ?string  $basePath deprecated, will be removed in next major version
      * @param integer $defaultVerbosity
      */
     public function __construct(
@@ -43,7 +43,12 @@ final class ExceptionPresenter
         private int $defaultVerbosity = OutputPrinter::VERBOSITY_NORMAL,
         ?ConfigurablePathPrinter $configurablePathPrinter = null,
     ) {
-        $this->configurablePathPrinter = $configurablePathPrinter ?? new ConfigurablePathPrinter($basePath, printAbsolutePaths: false);
+        // Historically, this class accepted a null (or not present) value for basePath. This was never passed by Behat,
+        // but was used by third parties to force the class to render exception traces with absolute file paths.
+        // The ConfigurablePathPrinter requires a value, but it is not used if printAbsolutePaths is true.
+        // Therefore, if the user provided null we can safely cast to '' (the working directory) and tell the printer
+        // to show absolute paths.
+        $this->configurablePathPrinter = $configurablePathPrinter ?? new ConfigurablePathPrinter($basePath ?? '', printAbsolutePaths: $basePath === null);
     }
 
     /**