rector: Rector analysis fails when using phar-distributed phpunit

Bug Report

Subject Details
Rector version 0.19.2

I have installed phpunit as a phar archive, and configured autoload_dev.php script that just requires a phar-file: require_once __DIR__.'/../bin/phpunit.phar'; to integrate phpunit.phar with phpstan and psalm static analysis tools. The same result may be achieved with bootstrapFiles phpstan configuration and autoload psalm attribute where phpunit.phar location may be specified so that tools will be aware of classes and methods provided by phpunit, but I created autoload_dev.php to keep things unified.

Finally I stumbled upon following issue when running rector with autoload_dev.php enabled:

> vendor/bin/rector process --dry-run --clear-cache -vvv
Script vendor/bin/rector process --dry-run --clear-cache -vvv handling the ci:rector event returned with error code 2

Surely, It disappears if I remove require_once statement from tests/autoload_dev.php:

-require_once __DIR__.'/../bin/phpunit.phar';

But then I get following diff from rector (RemoveParentCallWithoutParentRector):

    ---------- begin diff ----------
@@ @@

     private StackMiddleware $stack;

-    protected function setUp(): void
+    private function setUp(): void
     {
-        parent::setUp();
-
         $container = self::getContainer();

         /** @var ExceptionalValidationMiddleware $middleware */
    ----------- end diff -----------

Applied rules:
 * RemoveParentCallWithoutParentRector
 * PrivatizeFinalClassMethodRector

Basically It removes everything related to phpunit, since it is not aware of methods.

Minimal PHP Code Causing Issue

The example is not that minimal, but you may reproduce the issue on that commit:

https://github.com/phphd/exceptional-validation-bundle/commit/e9e5e4e70728edaec40858fdba31529e550c6000

Just run composer update and composer ci:rector and see what happens.

Expected Behaviour

It is expected that rector would handle phar-loaded classes the same way as phpstan and psalm does.

About this issue

  • Original URL
  • State: closed
  • Created 5 months ago
  • Comments: 26 (23 by maintainers)

Most upvoted comments

phpunit.phar is used as executable to be used as command itself, that’s why it doesn’t have file “bootstrap.php” or something2 autoload that user can use it as autoload

in contrast with phpstan.phar has “bootstrap.php” which people can use.

@rela589n After few hours of debugging, not sure if we can find solution now.

I’d recommend switching to normal PHPUnit package as obvious solution. There is no reason not to use those 3 tools together as composer dependencies, as Rector and PHPStan require PHP 7.2+ and have no blockers.

@TomasVotruba that’s not working, the tests needs in the paths(), not only src, and parent::setUp got removed:

1) tests/FooTest.php:10

    ---------- begin diff ----------
@@ @@
 {
     private Foo $foo;

-    protected function setUp(): void
+    private function setUp(): void
     {
-        parent::setUp();
-
         $this->foo = new Foo(234);

On bootstrap, the .phar by directly is loaded, but internally, it may has halt compiler which stop the process.

Ok, the reason why it always loaded is because you define

$rectorConfig->paths([__DIR__.'/']);

that will make it always loaded, even rector stubs is not loaded by bootstrap, which should only on the paths you need. I will create a PR to both rector-src and your repo for the solution 😃

@rela589n I am looking into it, the solution I found right now is by using Phar::loadPhar() syntax, see

that, running rector will succeed:

Screenshot 2024-01-30 at 05 44 49

@samsonasik That is whole bundle with other dependencies that would have to be removed to isolate the issue. We look for minimal reproducer like PHPUnit phar + single class + single rule.