`Type\nonnull()` is not narrowed by phpstan
Describe the bug
Type\nonnull() is not narrowed by phpstan
To Reproduce
<?php
require __DIR__.'/../vendor/autoload.php';
use Psl\Type;
/**
* @template T
*
* @param T|null $value
*
* @ara-assert nonnull $value
*
* @psalm-assert T $value
*
* @ara-return nonnull
*
* @return ($value is null ? never : T)
*/
function assertNotNull(mixed $value): mixed
{
}
function a(?int $i): void
{
\PHPStan\dumpType($i);
\PHPStan\dumpType(assertNotNull($i));
}
function b(?int $i): void
{
\PHPStan\dumpType($i);
\PHPStan\dumpType(Type\nonnull()->assert($i));
}
Expected behavior
First method shows a way (provided by @ondrejmirtes) that this can work in phpstan.
The second method use Type\nonnull().
The dumped types here should be
int|null followed by int for both dumpTypes. but we get:
27 Dumped type: int|null
28 Dumped type: int
33 Dumped type: int|null
34 Dumped type: mixed
The Psl version of the function "narrows" int|null to mixed, not int
You need to dump the type on the line after the assert.
This works as expected:
function b(?int $i): void
{
\PHPStan\dumpType($i);
Type\nonnull()->assert($i);
\PHPStan\dumpType($i);
}
The fact that the returned value is not correctly inferred might be a bug in PHPStan.
Thanks for looking like that. However, all the other PSL types work like i posted in the OP.
i.e. this does not need the dump to be on the line after the insert This works:
function c(?int $i): void
{
\PHPStan\dumpType($i);
\PHPStan\dumpType(Type\int()->assert($i));
}
Is this maybe what https://github.com/php-standard-library/phpstan-extension/blob/1.0.x/src/Type/AssertTypeSpecifyingExtension.php is handling, and is not working for Type\nonnull() for some reason?