Skip to content

Commit 6277fb4

Browse files
committed
Separate classes for new @param- tags
1 parent f4d1d48 commit 6277fb4

13 files changed

+268
-244
lines changed

src/Analyser/NodeScopeResolver.php

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -5660,6 +5660,7 @@ public function getPhpDocs(Scope $scope, Node\FunctionLike|Node\Stmt\Property $n
56605660
$varTags = [];
56615661
if ($resolvedPhpDoc !== null) {
56625662
$templateTypeMap = $resolvedPhpDoc->getTemplateTypeMap();
5663+
$phpDocImmediatelyInvokedCallableParameters = $resolvedPhpDoc->getParamsImmediatelyInvokedCallable();
56635664
foreach ($resolvedPhpDoc->getParamTags() as $paramName => $paramTag) {
56645665
if (array_key_exists($paramName, $phpDocParameterTypes)) {
56655666
continue;
@@ -5668,20 +5669,19 @@ public function getPhpDocs(Scope $scope, Node\FunctionLike|Node\Stmt\Property $n
56685669
if ($scope->isInClass()) {
56695670
$paramType = $this->transformStaticType($scope->getClassReflection(), $paramType);
56705671
}
5671-
$closureThisType = $paramTag->getClosureThisType();
5672-
if ($closureThisType !== null) {
5673-
if ($scope->isInClass()) {
5674-
$closureThisType = $this->transformStaticType($scope->getClassReflection(), $closureThisType);
5675-
}
5676-
$phpDocClosureThisTypeParameters[$paramName] = $closureThisType;
5677-
}
56785672
$phpDocParameterTypes[$paramName] = $paramType;
5679-
$immediatelyInvokedCallable = $paramTag->isImmediatelyInvokedCallable();
5680-
if ($immediatelyInvokedCallable->maybe()) {
5673+
}
5674+
foreach ($resolvedPhpDoc->getParamClosureThisTags() as $paramName => $paramClosureThisTag) {
5675+
if (array_key_exists($paramName, $phpDocClosureThisTypeParameters)) {
56815676
continue;
56825677
}
5683-
$phpDocImmediatelyInvokedCallableParameters[$paramName] = $immediatelyInvokedCallable->yes();
5678+
$paramClosureThisType = $paramClosureThisTag->getType();
5679+
if ($scope->isInClass()) {
5680+
$paramClosureThisType = $this->transformStaticType($scope->getClassReflection(), $paramClosureThisType);
5681+
}
5682+
$phpDocClosureThisTypeParameters[$paramName] = $paramClosureThisType;
56845683
}
5684+
56855685
foreach ($resolvedPhpDoc->getParamOutTags() as $paramName => $paramOutTag) {
56865686
$phpDocParameterOutTypes[$paramName] = $paramOutTag->getType();
56875687
}

src/PhpDoc/PhpDocNodeResolver.php

Lines changed: 39 additions & 68 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
use PHPStan\PhpDoc\Tag\MethodTag;
1212
use PHPStan\PhpDoc\Tag\MethodTagParameter;
1313
use PHPStan\PhpDoc\Tag\MixinTag;
14+
use PHPStan\PhpDoc\Tag\ParamClosureThisTag;
1415
use PHPStan\PhpDoc\Tag\ParamOutTag;
1516
use PHPStan\PhpDoc\Tag\ParamTag;
1617
use PHPStan\PhpDoc\Tag\PropertyTag;
@@ -30,14 +31,11 @@
3031
use PHPStan\PhpDocParser\Ast\PhpDoc\TemplateTagValueNode;
3132
use PHPStan\Reflection\PassedByReference;
3233
use PHPStan\Rules\PhpDoc\UnresolvableTypeHelper;
33-
use PHPStan\TrinaryLogic;
34-
use PHPStan\Type\CallableType;
3534
use PHPStan\Type\Generic\TemplateTypeFactory;
3635
use PHPStan\Type\Generic\TemplateTypeMap;
3736
use PHPStan\Type\Generic\TemplateTypeScope;
3837
use PHPStan\Type\Generic\TemplateTypeVariance;
3938
use PHPStan\Type\MixedType;
40-
use PHPStan\Type\ObjectWithoutClassType;
4139
use PHPStan\Type\Type;
4240
use PHPStan\Type\TypeCombinator;
4341
use function array_key_exists;
@@ -345,31 +343,6 @@ public function resolveTemplateTags(PhpDocNode $phpDocNode, NameScope $nameScope
345343
public function resolveParamTags(PhpDocNode $phpDocNode, NameScope $nameScope): array
346344
{
347345
$resolved = [];
348-
$immediatelyInvokedCallableParameters = [];
349-
foreach (['@param-immediately-invoked-callable', '@phpstan-param-immediately-invoked-callable'] as $tagName) {
350-
foreach ($phpDocNode->getParamImmediatelyInvokedCallableTagValues($tagName) as $tagValue) {
351-
$parameterName = substr($tagValue->parameterName, 1);
352-
$immediatelyInvokedCallableParameters[$parameterName] = TrinaryLogic::createYes();
353-
}
354-
}
355-
foreach (['@param-later-invoked-callable', '@phpstan-param-later-invoked-callable'] as $tagName) {
356-
foreach ($phpDocNode->getParamLaterInvokedCallableTagValues($tagName) as $tagValue) {
357-
$parameterName = substr($tagValue->parameterName, 1);
358-
$immediatelyInvokedCallableParameters[$parameterName] = TrinaryLogic::createNo();
359-
}
360-
}
361-
362-
$unusedImmediatelyInvokedCallableParameters = $immediatelyInvokedCallableParameters;
363-
364-
$closureThisTypes = [];
365-
foreach (['@param-closure-this', '@phpstan-param-closure-this'] as $tagName) {
366-
foreach ($phpDocNode->getParamClosureThisTagValues($tagName) as $tagValue) {
367-
$parameterName = substr($tagValue->parameterName, 1);
368-
$closureThisTypes[$parameterName] = TypeCombinator::intersect(new ObjectWithoutClassType(), $this->typeNodeResolver->resolve($tagValue->type, $nameScope));
369-
}
370-
}
371-
372-
$unusedClosureThisTypes = $closureThisTypes;
373346

374347
foreach (['@param', '@phan-param', '@psalm-param', '@phpstan-param'] as $tagName) {
375348
foreach ($phpDocNode->getParamTagValues($tagName) as $tagValue) {
@@ -379,53 +352,13 @@ public function resolveParamTags(PhpDocNode $phpDocNode, NameScope $nameScope):
379352
continue;
380353
}
381354

382-
if (array_key_exists($parameterName, $immediatelyInvokedCallableParameters)) {
383-
$immediatelyInvokedCallable = $immediatelyInvokedCallableParameters[$parameterName];
384-
unset($unusedImmediatelyInvokedCallableParameters[$parameterName]);
385-
} else {
386-
$immediatelyInvokedCallable = TrinaryLogic::createMaybe();
387-
}
388-
389-
if (array_key_exists($parameterName, $closureThisTypes)) {
390-
$closureThisType = $closureThisTypes[$parameterName];
391-
unset($unusedClosureThisTypes[$parameterName]);
392-
} else {
393-
$closureThisType = null;
394-
}
395-
396355
$resolved[$parameterName] = new ParamTag(
397356
$parameterType,
398357
$tagValue->isVariadic,
399-
$immediatelyInvokedCallable,
400-
$closureThisType,
401358
);
402359
}
403360
}
404361

405-
foreach ($unusedImmediatelyInvokedCallableParameters as $parameterName => $immediately) {
406-
if (array_key_exists($parameterName, $closureThisTypes)) {
407-
$closureThisType = $closureThisTypes[$parameterName];
408-
unset($unusedClosureThisTypes[$parameterName]);
409-
} else {
410-
$closureThisType = null;
411-
}
412-
$resolved[$parameterName] = new ParamTag(
413-
new CallableType(),
414-
false,
415-
$immediately,
416-
$closureThisType,
417-
);
418-
}
419-
420-
foreach ($unusedClosureThisTypes as $parameterName => $closureThisType) {
421-
$resolved[$parameterName] = new ParamTag(
422-
new CallableType(),
423-
false,
424-
TrinaryLogic::createMaybe(),
425-
$closureThisType,
426-
);
427-
}
428-
429362
return $resolved;
430363
}
431364

@@ -457,6 +390,44 @@ public function resolveParamOutTags(PhpDocNode $phpDocNode, NameScope $nameScope
457390
return $resolved;
458391
}
459392

393+
/**
394+
* @return array<string, bool>
395+
*/
396+
public function resolveParamImmediatelyInvokedCallable(PhpDocNode $phpDocNode): array
397+
{
398+
$parameters = [];
399+
foreach (['@param-immediately-invoked-callable', '@phpstan-param-immediately-invoked-callable'] as $tagName) {
400+
foreach ($phpDocNode->getParamImmediatelyInvokedCallableTagValues($tagName) as $tagValue) {
401+
$parameterName = substr($tagValue->parameterName, 1);
402+
$parameters[$parameterName] = true;
403+
}
404+
}
405+
foreach (['@param-later-invoked-callable', '@phpstan-param-later-invoked-callable'] as $tagName) {
406+
foreach ($phpDocNode->getParamLaterInvokedCallableTagValues($tagName) as $tagValue) {
407+
$parameterName = substr($tagValue->parameterName, 1);
408+
$parameters[$parameterName] = false;
409+
}
410+
}
411+
412+
return $parameters;
413+
}
414+
415+
/**
416+
* @return array<string, ParamClosureThisTag>
417+
*/
418+
public function resolveParamClosureThisTags(PhpDocNode $phpDocNode, NameScope $nameScope): array
419+
{
420+
$closureThisTypes = [];
421+
foreach (['@param-closure-this', '@phpstan-param-closure-this'] as $tagName) {
422+
foreach ($phpDocNode->getParamClosureThisTagValues($tagName) as $tagValue) {
423+
$parameterName = substr($tagValue->parameterName, 1);
424+
$closureThisTypes[$parameterName] = new ParamClosureThisTag($this->typeNodeResolver->resolve($tagValue->type, $nameScope));
425+
}
426+
}
427+
428+
return $closureThisTypes;
429+
}
430+
460431
public function resolveReturnTag(PhpDocNode $phpDocNode, NameScope $nameScope): ?ReturnTag
461432
{
462433
$resolved = null;

0 commit comments

Comments
 (0)