1

I have an issue after upgrade from PHP 7.3 to 8.1.1 There is lot to be done of course, but this is kind of weird. This example is not working for me with error Fatal error:

Uncaught Error: Class "TestC" not found in C:\xampp81\htdocs\helpdesk811\test81\index.php:2 Stack trace: #0 {main} thrown in C:\xampp81\htdocs\helpdesk811\test81\index.php on line 2

<?php
$a = new TestC;
echo $a->a;
class TestC
{
    public $a = "a_value";
    public $b;
    public function __toString()
    {
        return "string";
    }
}

If I define class and create instance later, it works, but I was not able to find any documentation for this behavior.It's the same with static method (public static function foo(){echo "bar";}).

I tried 3v4l.org sandbox and it works in versions >5.0 && <8.0

Dharman
  • 30,962
  • 25
  • 85
  • 135
Chada
  • 46
  • 5

2 Answers2

3

You can use a class before defining it, but only if early binding is allowed. Early binding does not work if some dependencies are not available yet, if the class uses traits or if it implements an interface. Since PHP 8 there is a new Stringable interface and every class that defines the __toString() function implicitly implements that interface, thus preventing early binding.

Nikita Popov (nikic) wrote an article about Early binding in PHP in which he mentions that this behavior is indeed not well documented.

Remon Huijts
  • 661
  • 6
  • 7
  • Thanks for explanation. In some project, this is huge change, but easily fixable (for me anyway). – Chada Feb 14 '22 at 23:02
  • @Chada it is indeed a backward compatibility break that may not have been intentional. I am not sure that this bug will be fixed in PHP, because it broke something that was never really supported or documented. – Remon Huijts Feb 16 '22 at 12:47
1

I was digging deeper and it looks like it's really the BUG. https://bugs.php.net/bug.php?id=79350

Chada
  • 46
  • 5
  • As it’s currently written, your answer is unclear. Please [edit] to add additional details that will help others understand how this addresses the question asked. You can find more information on how to write good answers [in the help center](/help/how-to-answer). – Community Jan 07 '22 at 22:02