Skip to content

Commit

Permalink
Fix looking for PHPDocs in trait in anonymous class in trait
Browse files Browse the repository at this point in the history
  • Loading branch information
ondrejmirtes committed Jan 6, 2022
1 parent 63838ee commit 11176c7
Show file tree
Hide file tree
Showing 5 changed files with 68 additions and 5 deletions.
13 changes: 10 additions & 3 deletions src/Type/FileTypeMapper.php
Original file line number Diff line number Diff line change
Expand Up @@ -205,7 +205,7 @@ private function resolvePhpDocStringToDocNode(string $phpDocString): PhpDocNode
private function getNameScopeMap(string $fileName): array
{
if (!isset($this->memoryCache[$fileName])) {
$cacheKey = sprintf('%s-phpdocstring-v15-shebang', $fileName);
$cacheKey = sprintf('%s-phpdocstring-v16-look-for-trait', $fileName);
$variableCacheKey = implode(',', array_map(static fn (array $file): string => sprintf('%s-%d', $file['filename'], $file['modifiedTime']), $this->getCachedDependentFilesWithTimestamps($fileName)));
$map = $this->cache->load($cacheKey, $variableCacheKey);

Expand Down Expand Up @@ -284,20 +284,24 @@ private function createNameScopeMap(
}
$namespace = null;

$traitFound = false;

/** @var array<string|null> $functionStack */
$functionStack = [];
$uses = [];
$this->processNodes(
$this->phpParser->parseFile($fileName),
function (Node $node) use ($fileName, $lookForTrait, $traitMethodAliases, $originalClassFileName, &$nameScopeMap, &$classStack, &$typeAliasStack, &$namespace, &$functionStack, &$uses, &$typeMapStack): ?int {
function (Node $node) use ($fileName, $lookForTrait, &$traitFound, $traitMethodAliases, $originalClassFileName, &$nameScopeMap, &$classStack, &$typeAliasStack, &$namespace, &$functionStack, &$uses, &$typeMapStack): ?int {
if ($node instanceof Node\Stmt\ClassLike) {
if ($lookForTrait !== null) {
if ($lookForTrait !== null && !$traitFound) {
if (!$node instanceof Node\Stmt\Trait_) {
return self::SKIP_NODE;
}
if ((string) $node->namespacedName !== $lookForTrait) {
return self::SKIP_NODE;
}

$traitFound = true;
} else {
if ($node->name === null) {
if (!$node instanceof Node\Stmt\Class_) {
Expand All @@ -308,6 +312,9 @@ function (Node $node) use ($fileName, $lookForTrait, $traitMethodAliases, $origi
} elseif ((bool) $node->getAttribute('anonymousClass', false)) {
$className = $node->name->name;
} else {
if ($traitFound) {
return self::SKIP_NODE;
}
$className = ltrim(sprintf('%s\\%s', $namespace, $node->name->name), '\\');
}
$classStack[] = $className;
Expand Down
17 changes: 15 additions & 2 deletions tests/PHPStan/Analyser/AnalyserIntegrationTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -500,18 +500,31 @@ public function testBug6300(): void
$this->assertSame(24, $errors[1]->getLine());
}

public function testBug6253(): void
{
$errors = $this->runAnalyse(
__DIR__ . '/data/bug-6253.php',
[
__DIR__ . '/data/bug-6253.php',
__DIR__ . '/data/bug-6253-app-scope-trait.php',
__DIR__ . '/data/bug-6253-collection-trait.php',
],
);
$this->assertNoErrors($errors);
}

/**
* @return Error[]
*/
private function runAnalyse(string $file): array
private function runAnalyse(string $file, ?array $allAnalysedFiles = null): array
{
$file = $this->getFileHelper()->normalizePath($file);
/** @var Analyser $analyser */
$analyser = self::getContainer()->getByType(Analyser::class);
/** @var FileHelper $fileHelper */
$fileHelper = self::getContainer()->getByType(FileHelper::class);
/** @var Error[] $errors */
$errors = $analyser->analyse([$file])->getErrors();
$errors = $analyser->analyse([$file], null, null, true, $allAnalysedFiles)->getErrors();
foreach ($errors as $error) {
$this->assertSame($fileHelper->normalizePath($file), $error->getFilePath());
}
Expand Down
22 changes: 22 additions & 0 deletions tests/PHPStan/Analyser/data/bug-6253-app-scope-trait.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
<?php

namespace Bug6253;

trait AppScopeTrait
{
/**
* @return int
*/
public function getApp()
{
return 1;
}

/**
* @return self
*/
public function setApp()
{
return new self();
}
}
13 changes: 13 additions & 0 deletions tests/PHPStan/Analyser/data/bug-6253-collection-trait.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<?php

namespace Bug6253;

trait CollectionTrait
{
public function doFoo(): void
{
$c = new class () {
use AppScopeTrait;
};
}
}
8 changes: 8 additions & 0 deletions tests/PHPStan/Analyser/data/bug-6253.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<?php

namespace Bug6253;

class CollectionMock
{
use CollectionTrait;
}

0 comments on commit 11176c7

Please sign in to comment.