Skip to content

Commit

Permalink
Fix test case for named variadic callable docblock
Browse files Browse the repository at this point in the history
  • Loading branch information
robchett committed Oct 7, 2023
1 parent c71a252 commit fc7f846
Show file tree
Hide file tree
Showing 2 changed files with 66 additions and 10 deletions.
46 changes: 45 additions & 1 deletion src/Psalm/Internal/Type/ParseTreeCreator.php
Original file line number Diff line number Diff line change
Expand Up @@ -235,6 +235,46 @@ private function createMethodParam(array $current_token, ParseTree $current_pare
$this->current_leaf = $new_parent_leaf;
}

/**
* @param array{0: string, 1: int, 2?: string} $current_token
*/
private function parseCallableParam(array $current_token, ParseTree $current_parent): void
{
$variadic = false;
$has_default = false;

if ($current_token[0] === '&') {
++$this->t;
$current_token = $this->t < $this->type_token_count ? $this->type_tokens[$this->t] : null;
} elseif ($current_token[0] === '...') {
$variadic = true;

++$this->t;
$current_token = $this->t < $this->type_token_count ? $this->type_tokens[$this->t] : null;
} elseif ($current_token[0] === '=') {
$has_default = true;

++$this->t;
$current_token = $this->t < $this->type_token_count ? $this->type_tokens[$this->t] : null;
}

if (!$current_token || $current_token[0][0] !== '$') {
throw new TypeParseTreeException('Unexpected token after space');
}

$new_leaf = new CallableParamTree($current_parent);
$new_leaf->has_default = $has_default;
$new_leaf->variadic = $variadic;

if ($current_parent !== $this->current_leaf) {
$new_leaf->children = [$this->current_leaf];
array_pop($current_parent->children);
}
$current_parent->children[] = $new_leaf;

$this->current_leaf = $new_leaf;
}

private function handleLessThan(): void
{
if (!$this->current_leaf instanceof FieldEllipsis) {
Expand Down Expand Up @@ -565,11 +605,15 @@ private function handleSpace(): void
throw new TypeParseTreeException('Unexpected space');
}

++$this->t;

if ($current_parent instanceof MethodTree) {
++$this->t;
$this->createMethodParam($next_token, $current_parent);
}
if ($current_parent instanceof CallableTree) {
++$this->t;
$this->parseCallableParam($next_token, $current_parent);
}
}

private function handleQuestionMark(): void
Expand Down
30 changes: 21 additions & 9 deletions tests/TypeAnnotationTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -686,11 +686,14 @@ class Foo {
* @psalm-type B callable(int, int=): string
* @psalm-type C callable(int $a, string $b): void
* @psalm-type D callable(string $c): mixed
* @psalm-type E callable(float...): (int|null)
* @psalm-type F callable(float ...$d): (int|null)
* @psalm-type G callable(array<int>): array<string>
* @psalm-type H callable(array<string, int> $e): array<int, string>
* @psalm-type I \Closure(int, int): string
* @psalm-type E callable(string $c): mixed
* @psalm-type F callable(float...): (int|null)
* @psalm-type G callable(float ...$d): (int|null)
* @psalm-type H callable(array<int>): array<string>
* @psalm-type I callable(array<string, int> $e): array<int, string>
* @psalm-type J callable(array<int> ...): string
* @psalm-type K callable(array<int> ...$e): string
* @psalm-type L \Closure(int, int): string
*
* @method ma(): A
* @method mb(): B
Expand All @@ -701,6 +704,9 @@ class Foo {
* @method mg(): G
* @method mh(): H
* @method mi(): I
* @method mj(): J
* @method mk(): K
* @method ml(): L
*/
class Foo {
public function __call(string $method, array $params) { return 1; }
Expand All @@ -716,17 +722,23 @@ public function __call(string $method, array $params) { return 1; }
$output_mg = $foo->mg();
$output_mh = $foo->mh();
$output_mi = $foo->mi();
$output_mj = $foo->mj();
$output_mk = $foo->mk();
$output_ml = $foo->ml();
',
'assertions' => [
'$output_ma===' => 'callable(int, int):string',
'$output_mb===' => 'callable(int, int=):string',
'$output_mc===' => 'callable(int, string):void',
'$output_md===' => 'callable(string):mixed',
'$output_me===' => 'callable(float...):(int|null)',
'$output_me===' => 'callable(string):mixed',
'$output_mf===' => 'callable(float...):(int|null)',
'$output_mg===' => 'callable(array<array-key, int>):array<array-key, string>',
'$output_mh===' => 'callable(array<string, int>):array<int, string>',
'$output_mi===' => 'Closure(int, int):string',
'$output_mg===' => 'callable(float...):(int|null)',
'$output_mh===' => 'callable(array<array-key, int>):array<array-key, string>',
'$output_mi===' => 'callable(array<string, int>):array<int, string>',
'$output_mj===' => 'callable(array<array-key, int>...):string',
'$output_mk===' => 'callable(array<array-key, int>...):string',
'$output_ml===' => 'Closure(int, int):string',
],
],
'unionOfStringsContainingBraceChar' => [
Expand Down

0 comments on commit fc7f846

Please sign in to comment.