sebastianbergmann / phpunit

The PHP Unit Testing framework.
https://phpunit.de/
BSD 3-Clause "New" or "Revised" License
19.69k stars 2.2k forks source link

Extending using <extensions><bootstrap> on BeforeTestMethodCalledSubscriber causes Segfault #5206

Closed markdwhite closed 1 year ago

markdwhite commented 1 year ago
Q A
PHPUnit version 10.0.7
PHP version PHP 8.1.2-1ubuntu2.10
Installation Method Composer 2.3.5

Summary

This is possibly a misunderstanding of correct implementation of new Event System

After refactoring of a test extension from PHPUnit 9 to PHPUnit 10, tests run successfully as expected. With JUnit output logging enabled the junit.xml is produced correctly. With Xdebug enabled and JUnit output logging disabled, all tests run as expected. With Xdebug enabled and JUnit output logging enabled, all tests run correctly and the junit.xml is produced correctly but a segfault is reported. With Xdebug enabled and JUnit output logging enabled, but the extension is removed from phpunit.xml, tests fail, but junit.xml is correct and there is no seg fault.

Current behavior

In PHPUnit 9, the following approach was used successfully to override "final" class designations to simplify testing:

phpunit.xml (extract):

<extensions>
        <extension class="Tests\BypassFinalHook" />
   </extensions>
   ....omitted....
   <logging>
    <junit outputFile="build/logs/junit.xml"/>
  </logging>

BypassFinalHook.php

namespace Tests;

use DG\BypassFinals;
use PHPUnit\Runner\BeforeTestHook;

class BypassFinalHook implements BeforeTestHook
{
    /**
     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
     */
    public function executeBeforeTest(string $test): void
    {
        BypassFinals::enable();
    }
}

With PHPUnit 10 this has been rewritten as:

phpunit.xml (extract):

<extensions>
    <bootstrap class="Tests\BypassFinalHook"/>
  </extensions>
   ....omitted....
   <logging>
    <junit outputFile="build/logs/junit.xml"/>
  </logging>

BypassFinalHook.php:

namespace Tests;

use PHPUnit\Runner\Extension\Extension as PhpunitExtension;
use PHPUnit\Runner\Extension\Facade as EventFacade;
use PHPUnit\Runner\Extension\ParameterCollection;
use PHPUnit\TextUI\Configuration\Configuration;

class BypassFinalHook implements PhpunitExtension
{
    public function bootstrap(
        Configuration $configuration,
        EventFacade $facade,
        ParameterCollection $parameters
    ): void {
        $facade->registerSubscriber(
            new BeforeTestMethodCalledSubscriber()
        );
    }
}

BeforeTestMethodCalledSubscriber.php:

namespace Tests;

use DG\BypassFinals;
use PHPUnit\Event\Test\BeforeTestMethodCalled;
use PHPUnit\Event\Test\BeforeTestMethodCalledSubscriber as Subscriber;

class BeforeTestMethodCalledSubscriber implements Subscriber
{
    public function __construct()
    {
        BypassFinals::enable();
    }

    /**
     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
     */
    public function notify(BeforeTestMethodCalled $event): void
    {
        // pass
    }
}

Output when xdebug and junit logging enable:

PHPUnit 10.0.7 by Sebastian Bergmann and contributors.

Runtime:       PHP 8.1.2-1ubuntu2.10 with Xdebug 3.1.2
Configuration: /var/www/XXXXXX/phpunit.xml

...............................................................  63 / 208 ( 30%)
............................................................... 126 / 208 ( 60%)
............................................................... 189 / 208 ( 90%)
...................                                             208 / 208 (100%)

Time: 00:10.327, Memory: 102.50 MB

OK (208 tests, 703 assertions)

Generating code coverage report in Clover XML format ... done [00:00.018]

Generating code coverage report in HTML format ... done [00:00.205]
Segmentation fault (core dumped)

There is no core dump in /var/crash to provide, though I'll do this if you tell me how to obtain a core dump.

composer info | sort:

barryvdh/laravel-debugbar          v3.8.0             PHP Debugbar integration for Laravel
beyondcode/laravel-dump-server     1.9.0              Symfony Var-Dump Server for Laravel
brick/math                         0.10.2             Arbitrary-precision arithmetic library
clue/stream-filter                 v1.6.0             A simple and modern approach to stream filte...
composer/pcre                      3.1.0              PCRE wrapping library that offers type-safe ...
composer/xdebug-handler            3.0.3              Restarts a process without Xdebug.
dflydev/dot-access-data            v3.0.2             Given a deep data structure, access data by ...
dg/bypass-finals                   v1.4.1             Removes final keyword from source code on-th...
doctrine/inflector                 2.0.6              PHP Doctrine Inflector is a small library th...
doctrine/lexer                     3.0.0              PHP Doctrine Lexer parser library that can b...
dragonmantank/cron-expression      v3.3.2             CRON for PHP: Calculate the next or previous...
driftingly/rector-laravel          0.14.2             Rector upgrades rules for Laravel Framework
egulias/email-validator            4.0.1              A library for validating emails against seve...
fakerphp/faker                     v1.21.0            Faker is a PHP library that generates fake d...
filp/whoops                        2.14.6             php error handling for cool kids
fruitcake/php-cors                 v1.2.0             Cross-origin resource sharing library for th...
graham-campbell/result-type        v1.1.0             An Implementation Of The Result Type
guzzlehttp/guzzle                  7.5.0              Guzzle is a PHP HTTP client library
guzzlehttp/promises                1.5.2              Guzzle promises library
guzzlehttp/psr7                    2.4.3              PSR-7 message implementation that also provi...
guzzlehttp/uri-template            v1.0.1             A polyfill class for uri_template of PHP
hamcrest/hamcrest-php              v2.0.1             This is the PHP port of Hamcrest Matchers
http-interop/http-factory-guzzle   1.2.0              An HTTP Factory using Guzzle PSR7
jean85/pretty-package-versions     2.0.5              A library to get pretty versions strings of ...
<redacted>/common           10.0.2             Common code for all XXX projects
laracasts/flash                    3.2.2              Easy flash notifications
laravelcollective/html             v6.4.0             HTML and Form Builders for the Laravel Frame...
laravel/dusk                       v7.6.1             Laravel Dusk provides simple end-to-end test...
laravel/framework                  v10.0.3            The Laravel Framework.
laravel/pint                       v0.2.4             An opinionated code formatter for PHP.
laravel/serializable-closure       v1.3.0             Laravel Serializable Closure provides an eas...
laravel/tinker                     v2.8.0             Powerful REPL for the Laravel framework.
league/commonmark                  2.3.9              Highly-extensible PHP Markdown parser which ...
league/config                      v1.2.0             Define configuration arrays with strict sche...
league/flysystem                   3.12.2             File storage abstraction for PHP
league/mime-type-detection         1.11.0             Mime-type detection for Flysystem
masterminds/html5                  2.7.6              An HTML5 parser and serializer.
maximebf/debugbar                  v1.18.2            Debug bar in the browser for php application
mockery/mockery                    1.5.1              Mockery is a simple yet flexible PHP mock ob...
monolog/monolog                    3.3.1              Sends your logs to files, sockets, inboxes, ...
myclabs/deep-copy                  1.11.0             Create deep copies (clones) of your objects
nesbot/carbon                      2.66.0             An API extension for DateTime that supports ...
nette/schema                       v1.2.3             📐 Nette Schema: validating data structure...
nette/utils                        v4.0.0             🛠  Nette Utils: lightweight utilities for...
nikic/php-parser                   v4.15.3            A PHP parser written in PHP
nunomaduro/collision               v7.0.3             Cli error handling for console/command-line ...
nunomaduro/larastan                2.4.1              Larastan - Discover bugs in your code withou...
nunomaduro/termwind                v1.15.1            Its like Tailwind CSS, but for the console.
nyholm/psr7                        1.5.1              A fast PHP7 implementation of PSR-7
ocramius/package-versions          2.7.0              Provides efficient querying for installed pa...
pdepend/pdepend                    2.12.1             Official version of pdepend to be handled wi...
phar-io/manifest                   2.0.3              Component for reading phar.io manifest infor...
phar-io/version                    3.2.1              Library for handling version information and...
php-http/client-common             2.6.0              Common HTTP Client implementations and tools...
php-http/discovery                 1.14.3             Finds installed HTTPlug implementations and ...
php-http/httplug                   2.3.0              HTTPlug, the HTTP client abstraction for PHP
php-http/message                   1.13.0             HTTP Message related tools
php-http/message-factory           v1.0.2             Factory interfaces for PSR-7 HTTP Message
php-http/promise                   1.1.0              Promise used for asynchronous HTTP requests
phpmd/phpmd                        2.13.0             PHPMD is a spin-off project of PHP Depend an...
phpmyadmin/sql-parser              5.7.0              A validating SQL lexer and parser with a foc...
phpoption/phpoption                1.9.0              Option Type for PHP
phpstan/phpstan                    1.9.17             PHPStan - PHP Static Analysis Tool
phpunit/php-code-coverage          10.0.0             Library that provides collection, processing...
phpunit/php-file-iterator          4.0.1              FilterIterator implementation that filters f...
phpunit/php-invoker                4.0.0              Invoke callables with a timeout
phpunit/php-text-template          3.0.0              Simple template engine.
phpunit/php-timer                  6.0.0              Utility class for timing
phpunit/phpunit                    10.0.7             The PHP Unit Testing framework.
php-webdriver/webdriver            1.14.0             A PHP client for Selenium WebDriver. Previou...
psr/container                      2.0.2              Common Container Interface (PHP FIG PSR-11)
psr/event-dispatcher               1.0.0              Standard interfaces for event handling.
psr/http-client                    1.0.1              Common interface for HTTP clients
psr/http-factory                   1.0.1              Common interfaces for PSR-7 HTTP message fac...
psr/http-message                   1.0.1              Common interface for HTTP messages
psr/log                            3.0.0              Common interface for logging libraries
psr/simple-cache                   3.0.0              Common interfaces for simple caching
psy/psysh                          v0.11.12           An interactive shell for modern PHP.
ralouphie/getallheaders            3.0.3              A polyfill for getallheaders.
ramsey/collection                  2.0.0              A PHP library for representing and manipulat...
ramsey/uuid                        4.7.3              A PHP library for generating and working wit...
rector/rector                      0.15.16            Instant Upgrade and Automated Refactoring of...
roave/security-advisories          dev-master fd5adf7 Prevents installation of composer packages w...
sebastian/cli-parser               2.0.0              Library for parsing CLI options
sebastian/code-unit                2.0.0              Collection of value objects that represent t...
sebastian/code-unit-reverse-lookup 3.0.0              Looks up which function or method a line of ...
sebastian/comparator               5.0.0              Provides the functionality to compare PHP va...
sebastian/complexity               3.0.0              Library for calculating the complexity of PH...
sebastian/diff                     5.0.0              Diff implementation
sebastian/environment              6.0.0              Provides functionality to handle HHVM/PHP en...
sebastian/exporter                 5.0.0              Provides the functionality to export PHP var...
sebastian/global-state             6.0.0              Snapshotting of global state
sebastian/lines-of-code            2.0.0              Library for counting the lines of code in PH...
sebastian/object-enumerator        5.0.0              Traverses array structures and object graphs...
sebastian/object-reflector         3.0.0              Allows reflection of object attributes, incl...
sebastian/recursion-context        5.0.0              Provides functionality to recursively proces...
sebastian/type                     4.0.0              Collection of value objects that represent t...
sebastian/version                  4.0.1              Library that helps with managing the version...
sentry/sdk                         3.3.0              This is a metapackage shipping sentry/sentry...
sentry/sentry                      3.13.1             A PHP SDK for Sentry (http://sentry.io)
sentry/sentry-laravel              3.2.0              Laravel SDK for Sentry (https://sentry.io)
spatie/backtrace                   1.2.1              A better backtrace
spatie/flare-client-php            1.3.5              Send PHP errors to Flare
spatie/ignition                    1.4.3              A beautiful error page for PHP applications.
spatie/laravel-csp                 2.8.3              Add CSP headers to the responses of a Larave...
spatie/laravel-ignition            2.0.0              A beautiful error page for Laravel applicati...
spatie/laravel-package-tools       1.14.1             Tools for creating Laravel packages
squizlabs/php_codesniffer          3.7.1              PHP_CodeSniffer tokenizes PHP, JavaScript an...
symfony/config                     v6.2.5             Helps you find, load, combine, autofill and ...
symfony/console                    v6.2.5             Eases the creation of beautiful and testable...
symfony/css-selector               v6.2.5             Converts CSS selectors to XPath expressions
symfony/dependency-injection       v6.2.6             Allows you to standardize and centralize the...
symfony/deprecation-contracts      v3.2.0             A generic function and convention to trigger...
symfony/dom-crawler                v6.2.5             Eases DOM navigation for HTML and XML documents
symfony/error-handler              v6.2.5             Provides tools to manage errors and ease deb...
symfony/event-dispatcher-contracts v3.2.0             Generic abstractions related to dispatching ...
symfony/event-dispatcher           v6.2.5             Provides tools that allow your application c...
symfony/filesystem                 v6.2.5             Provides basic utilities for the filesystem
symfony/finder                     v6.2.5             Finds files and directories via an intuitive...
symfony/http-client-contracts      v3.2.0             Generic abstractions related to HTTP clients
symfony/http-client                v6.2.6             Provides powerful methods to fetch HTTP reso...
symfony/http-foundation            v6.2.6             Defines an object-oriented layer for the HTT...
symfony/http-kernel                v6.2.6             Provides a structured process for converting...
symfony/mailer                     v6.2.5             Helps sending emails
symfony/mime                       v6.2.5             Allows manipulating MIME messages
symfony/options-resolver           v6.2.5             Provides an improved replacement for the arr...
symfony/polyfill-ctype             v1.27.0            Symfony polyfill for ctype functions
symfony/polyfill-intl-grapheme     v1.27.0            Symfony polyfill for intl's grapheme_* funct...
symfony/polyfill-intl-idn          v1.27.0            Symfony polyfill for intl's idn_to_ascii and...
symfony/polyfill-intl-normalizer   v1.27.0            Symfony polyfill for intl's Normalizer class...
symfony/polyfill-mbstring          v1.27.0            Symfony polyfill for the Mbstring extension
symfony/polyfill-php72             v1.27.0            Symfony polyfill backporting some PHP 7.2+ f...
symfony/polyfill-php80             v1.27.0            Symfony polyfill backporting some PHP 8.0+ f...
symfony/polyfill-uuid              v1.27.0            Symfony polyfill for uuid functions
symfony/process                    v6.2.5             Executes commands in sub-processes
symfony/psr-http-message-bridge    v2.1.4             PSR HTTP message bridge
symfony/routing                    v6.2.5             Maps an HTTP request to a set of configurati...
symfony/service-contracts          v3.2.0             Generic abstractions related to writing serv...
symfony/string                     v6.2.5             Provides an object-oriented API to strings a...
symfony/translation-contracts      v3.2.0             Generic abstractions related to translation
symfony/translation                v6.2.5             Provides tools to internationalize your appl...
symfony/uid                        v6.2.5             Provides an object-oriented API to generate ...
symfony/var-dumper                 v6.2.5             Provides mechanisms for walking through any ...
symfony/var-exporter               v6.2.5             Allows exporting any serializable PHP data s...
theseer/tokenizer                  1.2.1              A small library for converting tokenized PHP...
tijsverkoyen/css-to-inline-styles  2.2.6              CssToInlineStyles is a class that enables yo...
vlucas/phpdotenv                   v5.5.0             Loads environment variables from `.env` to `...
voku/portable-ascii                2.0.1              Portable ASCII library - performance optimiz...    
webmozart/assert                   1.11.0             Assertions to validate method input/output w...

How to reproduce

Not sure. This may be down to incorrect implementation of the Event System by me.

Expected behavior

Execution without segfault.

sebastianbergmann commented 1 year ago

You have found a problem in the PHP runtime that leads to a segmentation fault. An issue like this has to be reported here using a minimal, self-contained, reproducing test case.

Please note that a test case that needs to be run through PHPUnit does not qualify as either "minimal" or "self-contained" when reporting bugs for the PHP runtime. Best practices for reporting bugs in PHP are documented here.