phpunit icon indicating copy to clipboard operation
phpunit copied to clipboard

Deprecations triggered when parsing an auto-loaded class are not displayed

Open jf-leblancrichard opened this issue 1 month ago • 6 comments

Q A
PHPUnit version 12.4.5
PHP version 8.5.0
Installation Method Composer

composer info | sort:

myclabs/deep-copy            1.13.4 Create deep copies (clones) of your objects
nikic/php-parser             5.6.2  A PHP parser written in PHP
phar-io/manifest             2.0.4  Component for reading phar.io manifest information fro...
phar-io/version              3.2.1  Library for handling version information and constraints
phpunit/php-code-coverage    12.5.0 Library that provides collection, processing, and rend...
phpunit/php-file-iterator    6.0.0  FilterIterator implementation that filters files based...
phpunit/php-invoker          6.0.0  Invoke callables with a timeout
phpunit/php-text-template    5.0.0  Simple template engine.
phpunit/php-timer            8.0.0  Utility class for timing
phpunit/phpunit              12.4.5 The PHP Unit Testing framework.
sebastian/cli-parser         4.2.0  Library for parsing CLI options
sebastian/comparator         7.1.3  Provides the functionality to compare PHP values for e...
sebastian/complexity         5.0.0  Library for calculating the complexity of PHP code units
sebastian/diff               7.0.0  Diff implementation
sebastian/environment        8.0.3  Provides functionality to handle HHVM/PHP environments
sebastian/exporter           7.0.2  Provides the functionality to export PHP variables for...
sebastian/global-state       8.0.2  Snapshotting of global state
sebastian/lines-of-code      4.0.0  Library for counting the lines of code in PHP source code
sebastian/object-enumerator  7.0.0  Traverses array structures and object graphs to enumer...
sebastian/object-reflector   5.0.0  Allows reflection of object attributes, including inhe...
sebastian/recursion-context  7.0.1  Provides functionality to recursively process PHP vari...
sebastian/type               6.0.3  Collection of value objects that represent the types o...
sebastian/version            6.0.0  Library that helps with managing the version number of...
staabm/side-effects-detector 1.0.5  A static analysis tool to detect side effects in PHP code
theseer/tokenizer            1.3.1  A small library for converting tokenized PHP source co...

vendor/bin/phpunit --check-php-configuration:

PHPUnit 12.4.5 by Sebastian Bergmann and contributors.

Checking whether PHP is configured according to https://docs.phpunit.de/en/12.4/installation.html#configuring-php-for-development

display_errors = On         ... ok
display_startup_errors = On ... ok
error_reporting = -1        ... ok
zend.assertions = 1         ... ok
assert.exception = 1        ... ok
memory_limit = -1           ... ok

Summary

Deprecations triggered when parsing an auto-loaded class are not displayed.

Current behavior

Following the steps below does not display any deprecation.

How to reproduce

Create the following files in a new empty directory:

composer.json:

{
    "autoload": {
        "psr-4": {
            "Bug\\": "src/"
        }
    },
    "autoload-dev": {
        "psr-4": {
            "Bug\\Tests\\": "tests/"
        }
    },
    "require-dev": {
        "phpunit/phpunit": "^12.4"
    }
}

phpunit.xml:

<?xml version="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:noNamespaceSchemaLocation="vendor/phpunit/phpunit/phpunit.xsd"
         bootstrap="vendor/autoload.php"
         cacheDirectory=".phpunit.cache"
         executionOrder="depends,defects"
         requireCoverageMetadata="true"
         beStrictAboutCoverageMetadata="true"
         beStrictAboutOutputDuringTests="true"
         displayDetailsOnPhpunitDeprecations="true"
         failOnPhpunitDeprecation="true"
         failOnRisky="true"
         failOnWarning="true">
    <testsuites>
        <testsuite name="default">
            <directory>tests</directory>
        </testsuite>
    </testsuites>

    <source ignoreIndirectDeprecations="true" restrictNotices="true" restrictWarnings="true">
        <include>
            <directory>src</directory>
            <!-- Uncomment to get the deprecation to display. -->
            <!-- <file>vendor/composer/ClassLoader.php</file> -->
        </include>
    </source>
</phpunit>

src/Deprecated.php:

<?php

declare(strict_types=1);

namespace Bug;

final class Deprecated
{
    public function __construct(int $deprecated = null) // should trigger "Implicitly marking parameter $deprecated as nullable is deprecated, the explicit nullable type must be used instead"
    {

    }
}

tests/DeprecatedTest.php:

<?php

declare(strict_types=1);

namespace Bug\Tests;

use Bug\Deprecated;
use PHPUnit\Framework\Attributes\CoversClass;
use PHPUnit\Framework\TestCase;

#[CoversClass(Deprecated::class)]
final class DeprecatedTest extends TestCase
{
    public function testDeprecated(): void
    {
        $this->assertNotNull(new Deprecated());
    }
}

Generate the vendor/autoload.php file by running composer dump-autoload.

Run vendor/bin/phpunit --display-deprecations and notice that no deprecation is displayed.

Expected behavior

Following the reproduction steps above should display the following deprecation:

Bug\Deprecated::__construct(): Implicitly marking parameter $deprecated as nullable is deprecated, the explicit nullable type must be used instead

A workaround is to uncomment the <file> element in phpunit.xml. Another workaround is to set ignoreIndirectDeprecations="false".

jf-leblancrichard avatar Dec 04 '25 15:12 jf-leblancrichard

This should be handled by #6165 and #6357.

CC @soyuka @nicolas-grekas

sebastianbergmann avatar Dec 04 '25 16:12 sebastianbergmann

I find it a bit odd that within a couple of hours this issue as well as #6434 and #6435 were reported. Is this, by chance, related to either #6434 or #6435? Thank you!

sebastianbergmann avatar Dec 05 '25 05:12 sebastianbergmann

My take would be it is related to the question of how to classify this error as self/direct/indirect.

~But, the error is generated from PHP core, right? It's not an E_USER_DEPRECATED error, and I am not sure if either the src/Deprecated.php or tests/DeprecatedTest.php files are on the stack trace at the time it is triggered.~ Does it matter that it is an E_DEPRECATED error? The source file reported for the error is the file containing the class, like it would be in the case of #6165.

I have added a https://github.com/sebastianbergmann/phpunit/issues/6434#issuecomment-3616851524 that autoload situations might need a different handling.

Regarding temporal coincidence, everyone in the Symfony pond is currently scrambling and trying to gather as many deprecation notices from their code base as possible, so we tend to notice what's missing :-).

mpdude avatar Dec 05 '25 13:12 mpdude

Does it matter that it is an E_DEPRECATED error?

It should not, as @nicolas-grekas added support for E_DEPRECATED in #6357.

sebastianbergmann avatar Dec 05 '25 13:12 sebastianbergmann

I find it a bit odd that within a couple of hours this issue as well as #6434 and #6435 were reported. Is this, by chance, related to either #6434 or #6435? Thank you!

@sebastianbergmann I hadn't seen either of those issues when I created this one. What prompted the discovery of this issue in our case is that some deprecations started popping up after upgrading PHP, but only when running our code outside of PHPUnit.

jf-leblancrichard avatar Dec 05 '25 13:12 jf-leblancrichard

I find it a bit odd that within a couple of hours this issue as well as #6434 and #6435 were reported. Is this, by chance, related to either #6434 or #6435? Thank you!

@sebastianbergmann I hadn't seen either of those issues when I created this one. What prompted the discovery of this issue in our case is that some deprecations started popping up after upgrading PHP, but only when running our code outside of PHPUnit.

I just noticed the two issues above are newer than mine, but if the question is if I was involved with those, the answer is no. My suspicion as to why these were all reported within a couple of hours is that PHP 8.1 security support will be dropped at the end of the month, so people are upgrading to newer PHP versions and are noticing the new deprecation warnings. That was the case for us at least...

jf-leblancrichard avatar Dec 05 '25 14:12 jf-leblancrichard