Impossible intersection types are not checked at compile time
Description
The following code:
<?php
class Foo {}
class Bar {}
function test(Foo&Bar $arg): void {}
https://3v4l.org/sKIr0
I use intersection type Foo&Bar for function argument.
Actually, there is no type that would be comparable to Foo&Bar. Therefore, Foo&Bar is equivalent to the type never.
If i use never in argument type, PHP Fatal Error will be thrown. But if i use Foo&Bar, no error will occur.
Resulted in this output:
Nothing
But I expected this output instead:
PHP Fatal error: Foo&Bar cannot be used as a parameter type
PHP Version
PHP 8.3.11
Operating System
Ubuntu 20.04
Hi @Kenny1911. This is something static analysis can help you with. IMO, this doesn't need solving in the PHP engine, as it will just add more runtime burden. @Girgias thoughts?
https://phpstan.org/r/a1a9efce-9725-40d1-818a-595a25e65c12
@iluuu1994 , however PHP does check int&float, for example. Is it difficult to check this as well?
however PHP does check int&float, for example
That's not quite the same:
Fatal error: Type int cannot be part of an intersection type
The engine makes assertions about members of intersection types being class types.
I'm not sure about hard, but at least for Foo&Bar, it would necessarily have to happen at runtime, when both types are available.
@iluuu1994 , however PHP does check
int&float, for example. Is it difficult to check this as well?
Yes, as currently class-types are not loaded at compile time except where necessary (for variance checks).
Changing this behaviour would at least require an RFC to allow the engine to autoload classes where previously it was not required.
Checking for int&float is easy as they are built-in types.
Right. Given this would either require to:
- delay the type check until both types are loaded, for which he have no trigger
- change behavior and autoload prematurely
I don't think this should be solved.
I agree to WONTFIX, but we should probably improve the documentation on intersection types.
Just to note, that this is described in the type declaration page of the documentation.