Skip to content

Commit

Permalink
Merge pull request #10691 from weirdan/10170-reports-unknown-static-m…
Browse files Browse the repository at this point in the history
…ethods-in-first-class-callables
  • Loading branch information
weirdan committed Feb 11, 2024
2 parents ceaea62 + a8c093a commit 13ebb91
Show file tree
Hide file tree
Showing 2 changed files with 42 additions and 1 deletion.
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
use Psalm\Issue\InvalidStringClass;
use Psalm\Issue\MixedMethodCall;
use Psalm\Issue\UndefinedClass;
use Psalm\Issue\UndefinedMethod;
use Psalm\IssueBuffer;
use Psalm\Node\Expr\VirtualArray;
use Psalm\Node\Expr\VirtualArrayItem;
Expand Down Expand Up @@ -490,6 +491,7 @@ private static function handleNamedCall(
$method_name_lc,
);


if ($stmt->isFirstClassCallable()) {
if ($found_method_and_class_storage) {
[ $method_storage ] = $found_method_and_class_storage;
Expand All @@ -515,8 +517,31 @@ private static function handleNamedCall(
$codebase->getMethodReturnType($method_id, $fq_class_name),
$codebase->methods->getStorage($declaring_method_id)->pure,
)]);
} elseif ($codebase->methodExists(
$call_static_method_id = new MethodIdentifier($method_id->fq_class_name, '__callstatic'),
new CodeLocation($statements_analyzer, $stmt),
null,
null,
false,
)) {
$return_type_candidate = new Union([new TClosure(
'Closure',
null,
$codebase->getMethodReturnType($call_static_method_id, $fq_class_name),
$codebase->methods->getStorage($call_static_method_id)->pure,
)]);
} else {
// FIXME: perhaps Psalm should complain about nonexisting method here, or throw a logic exception?
if (IssueBuffer::accepts(
new UndefinedMethod(
'Method ' . $method_id . ' does not exist',
new CodeLocation($statements_analyzer, $stmt),
(string) $method_id,
),
$statements_analyzer->getSuppressedIssues(),
)) {
return false;
}

$return_type_candidate = Type::getClosure();
}
}
Expand Down
16 changes: 16 additions & 0 deletions tests/MethodCallTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -1805,6 +1805,22 @@ public function foo(callable $_a = "strlen"): void {}
PHP,
'error_message' => 'TooManyArguments',
],
'firstClassCallableWithUnknownStaticMethod' => [
'code' => <<<'PHP'
<?php
class A {}
$_a = A::foo(...);
PHP,
'error_message' => 'UndefinedMethod',
],
'firstClassCallableWithUnknownInstanceMethod' => [
'code' => <<<'PHP'
<?php
class A {}
$_a = (new A)->foo(...);
PHP,
'error_message' => 'UndefinedMethod',
],
];
}
}

0 comments on commit 13ebb91

Please sign in to comment.