mirror of
https://github.com/danog/psalm.git
synced 2024-11-30 04:39:00 +01:00
Add support for class concats when checking for callables
This commit is contained in:
parent
1d5759a35c
commit
e6cf9e96df
@ -1238,6 +1238,7 @@ class CallChecker
|
||||
if (!$closure_type instanceof Type\Atomic\Fn) {
|
||||
if (!$closure_arg->value instanceof PhpParser\Node\Scalar\String_
|
||||
&& !$closure_arg->value instanceof PhpParser\Node\Expr\Array_
|
||||
&& !$closure_arg->value instanceof PhpParser\Node\Expr\BinaryOp\Concat
|
||||
) {
|
||||
return;
|
||||
}
|
||||
@ -1720,6 +1721,7 @@ class CallChecker
|
||||
}
|
||||
} elseif ($input_expr instanceof PhpParser\Node\Scalar\String_
|
||||
|| $input_expr instanceof PhpParser\Node\Expr\Array_
|
||||
|| $input_expr instanceof PhpParser\Node\Expr\BinaryOp\Concat
|
||||
) {
|
||||
foreach ($param_type->getTypes() as $param_type_part) {
|
||||
if ($param_type_part instanceof TClassString
|
||||
@ -1921,7 +1923,8 @@ class CallChecker
|
||||
}
|
||||
|
||||
/**
|
||||
* @param PhpParser\Node\Scalar\String_|PhpParser\Node\Expr\Array_ $callable_arg
|
||||
* @param PhpParser\Node\Scalar\String_|PhpParser\Node\Expr\Array_|PhpParser\Node\Expr\BinaryOp\Concat
|
||||
* $callable_arg
|
||||
*
|
||||
* @return string[]
|
||||
*/
|
||||
@ -1929,6 +1932,21 @@ class CallChecker
|
||||
\Psalm\FileSource $file_source,
|
||||
$callable_arg
|
||||
) {
|
||||
if ($callable_arg instanceof PhpParser\Node\Expr\BinaryOp\Concat) {
|
||||
if ($callable_arg->left instanceof PhpParser\Node\Expr\ClassConstFetch
|
||||
&& $callable_arg->left->class instanceof PhpParser\Node\Name
|
||||
&& $callable_arg->left->name instanceof PhpParser\Node\Identifier
|
||||
&& strtolower($callable_arg->left->name->name) === 'class'
|
||||
&& !in_array(strtolower($callable_arg->left->class->parts[0]), ['self', 'static', 'parent'])
|
||||
&& $callable_arg->right instanceof PhpParser\Node\Scalar\String_
|
||||
&& preg_match('/^::[A-Za-z0-9]+$/', $callable_arg->right->value)
|
||||
) {
|
||||
return [(string) $callable_arg->left->class->getAttribute('resolvedName') . $callable_arg->right->value];
|
||||
}
|
||||
|
||||
return [];
|
||||
}
|
||||
|
||||
if ($callable_arg instanceof PhpParser\Node\Scalar\String_) {
|
||||
return [preg_replace('/^\\\/', '', $callable_arg->value)];
|
||||
}
|
||||
|
@ -129,6 +129,7 @@ class CallableTest extends TestCase
|
||||
function foo(callable $c): void {}
|
||||
|
||||
foo("A::bar");
|
||||
foo(A::class . "::bar");
|
||||
foo(["A", "bar"]);
|
||||
foo([A::class, "bar"]);
|
||||
$a = new A();
|
||||
@ -625,7 +626,7 @@ class CallableTest extends TestCase
|
||||
'error_message' => 'InvalidFunctionCall',
|
||||
'error_levels' => ['UndefinedClass'],
|
||||
],
|
||||
'undefinedCallableMethod' => [
|
||||
'undefinedCallableMethodFullString' => [
|
||||
'<?php
|
||||
class A {
|
||||
public static function bar(string $a): string {
|
||||
@ -638,6 +639,45 @@ class CallableTest extends TestCase
|
||||
foo("A::barr");',
|
||||
'error_message' => 'UndefinedMethod',
|
||||
],
|
||||
'undefinedCallableMethodClassConcat' => [
|
||||
'<?php
|
||||
class A {
|
||||
public static function bar(string $a): string {
|
||||
return $a . "b";
|
||||
}
|
||||
}
|
||||
|
||||
function foo(callable $c): void {}
|
||||
|
||||
foo(A::class . "::barr");',
|
||||
'error_message' => 'UndefinedMethod',
|
||||
],
|
||||
'undefinedCallableMethodArray' => [
|
||||
'<?php
|
||||
class A {
|
||||
public static function bar(string $a): string {
|
||||
return $a . "b";
|
||||
}
|
||||
}
|
||||
|
||||
function foo(callable $c): void {}
|
||||
|
||||
foo([A::class, "::barr"]);',
|
||||
'error_message' => 'UndefinedMethod',
|
||||
],
|
||||
'undefinedCallableMethodArrayWithoutClass' => [
|
||||
'<?php
|
||||
class A {
|
||||
public static function bar(string $a): string {
|
||||
return $a . "b";
|
||||
}
|
||||
}
|
||||
|
||||
function foo(callable $c): void {}
|
||||
|
||||
foo(["A", "::barr"]);',
|
||||
'error_message' => 'UndefinedMethod',
|
||||
],
|
||||
'undefinedCallableMethodClass' => [
|
||||
'<?php
|
||||
class A {
|
||||
|
Loading…
Reference in New Issue
Block a user