Skip to content
Closed
Show file tree
Hide file tree
Changes from 2 commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
b94b5d6
Fix false positives for is_a() and instanceof checks on $this in traits
github-actions[bot] Mar 10, 2026
4fc6007
Generalize trait $this check to cover property fetches and method calls
phpstan-bot Mar 14, 2026
af1247c
Handle static access, nullsafe access, and $this:: in trait $this check
phpstan-bot Mar 14, 2026
6b9535d
Fix BooleanNot false positive for $this-dependent checks in traits
phpstan-bot Mar 14, 2026
5ac5e5f
Move isExpressionDependentOnThis to ExpressionDependsOnThisHelper
phpstan-bot Mar 14, 2026
ba6e8f3
Fix method_exists($this) false positives in traits and PHP 7.4 lint
phpstan-bot Mar 14, 2026
b18a0b0
Add regression tests for trait-related false positives
phpstan-bot Mar 14, 2026
4f8d0b3
Still report method_exists($this) as always true when method is defin…
phpstan-bot Mar 14, 2026
6d73f01
Extend trait context detection to cover self-typed variables and fix …
phpstan-bot Mar 14, 2026
44458d8
Fix lint errors and skip testBug7599 on PHP < 8.1
phpstan-bot Mar 14, 2026
ee69212
Add regression test for phpstan/phpstan#12798
phpstan-bot Mar 14, 2026
8f559bc
Add test
VincentLanglet Mar 14, 2026
cb69e3e
Rework
VincentLanglet Mar 14, 2026
cb0a2e5
Simplify
VincentLanglet Mar 14, 2026
9ba6146
Remove dedicated class
VincentLanglet Mar 14, 2026
1c6d393
Fix test
VincentLanglet Mar 14, 2026
53eb552
Reduce visibility
VincentLanglet Mar 15, 2026
c86721e
Add test
VincentLanglet Mar 15, 2026
9fa10d3
Add tests
VincentLanglet Mar 15, 2026
7e49d26
Add trait context awareness to comparison rules
phpstan-bot Mar 15, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 27 additions & 0 deletions src/Rules/Comparison/ImpossibleCheckTypeHelper.php
Original file line number Diff line number Diff line change
Expand Up @@ -310,6 +310,11 @@ public function findSpecifiedType(
continue;
}

if ($scope->isInTrait() && self::isExpressionDependentOnThis($sureType[0])) {
$results[] = TrinaryLogic::createMaybe();
continue;
}

if ($this->treatPhpDocTypesAsCertain) {
$argumentType = $scope->getType($sureType[0]);
} else {
Expand All @@ -336,6 +341,11 @@ public function findSpecifiedType(
continue;
}

if ($scope->isInTrait() && self::isExpressionDependentOnThis($sureNotType[0])) {
$results[] = TrinaryLogic::createMaybe();
continue;
}

if ($this->treatPhpDocTypesAsCertain) {
$argumentType = $scope->getType($sureNotType[0]);
} else {
Expand Down Expand Up @@ -381,6 +391,23 @@ private static function isSpecified(Scope $scope, Expr $node, Expr $expr): bool
) && $scope->hasExpressionType($expr)->yes();
}

private static function isExpressionDependentOnThis(Expr $expr): bool
{
if ($expr instanceof Expr\Variable && $expr->name === 'this') {
return true;
}

if ($expr instanceof Expr\PropertyFetch) {
return self::isExpressionDependentOnThis($expr->var);
}

if ($expr instanceof Expr\MethodCall) {
return self::isExpressionDependentOnThis($expr->var);
}

return false;
}

/**
* @param Node\Arg[] $args
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1207,4 +1207,10 @@ public function testBug13799(): void
]);
}

public function testBug13023(): void
{
$this->treatPhpDocTypesAsCertain = true;
$this->analyse([__DIR__ . '/data/bug-13023.php'], []);
}

}
52 changes: 52 additions & 0 deletions tests/PHPStan/Rules/Comparison/data/bug-13023.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
<?php declare(strict_types = 1);

namespace Bug13023;

class SomeClass
{
use MyTrait;
}

class SomeClass2
{
use MyTrait;
}

trait MyTrait
{
public function getRandom(): int
{
$value = random_int(1, 100);
if (is_a($this, SomeClass::class)) {
return $value * $value;
}
return $value;
}
}

class SomeClass3
{
use MyTrait2;

public string $foo = 'foo';
}

class SomeClass4
{
use MyTrait2;

public int $foo = 1;
}

trait MyTrait2
{
public function getRandom(): int
{
$value = random_int(1, 100);
if (\is_int($this->foo)) {
return $value * $value;
}

return $value;
}
}
Loading