From ed9043b43ceb7d44aa60286eeb08c9de6cc8b169 Mon Sep 17 00:00:00 2001 From: Joe Hoyle Date: Sun, 24 Jan 2021 13:29:21 -0500 Subject: [PATCH] Support completions on class references (#5085) * Support compleitions on class references This provides completions on class references (as opposed to initiated objects via the type map), so you can do `MyClass::` and get completitions for static methods and constants etc. * Only provide completions for references that don't exist --- src/Psalm/Codebase.php | 11 +++++++- src/Psalm/Internal/Codebase/Analyzer.php | 3 +++ tests/LanguageServer/CompletionTest.php | 32 ++++++++++++++++++++++++ 3 files changed, 45 insertions(+), 1 deletion(-) diff --git a/src/Psalm/Codebase.php b/src/Psalm/Codebase.php index 30185fa0c..607d6f8b3 100644 --- a/src/Psalm/Codebase.php +++ b/src/Psalm/Codebase.php @@ -1279,7 +1279,16 @@ class Codebase } foreach ($reference_map as $start_pos => [$end_pos, $possible_reference]) { - if ($offset < $start_pos || $possible_reference[0] !== '*') { + if ($offset < $start_pos) { + continue; + } + // If the reference precedes a "::" then treat it as a class reference. + if ($offset - $end_pos === 2 && substr($file_contents, $end_pos, 2) === '::') { + return [$possible_reference, '::', $offset]; + } + + // Only continue for references that are partial / don't exist. + if ($possible_reference[0] !== '*') { continue; } diff --git a/src/Psalm/Internal/Codebase/Analyzer.php b/src/Psalm/Internal/Codebase/Analyzer.php index 2688c3229..5e4065549 100644 --- a/src/Psalm/Internal/Codebase/Analyzer.php +++ b/src/Psalm/Internal/Codebase/Analyzer.php @@ -1172,6 +1172,9 @@ class Analyzer ]; } + /** + * @param string $reference The symbol name for the reference. Prepend with an asterisk (*) to signify a reference that doesn't exist. + */ public function addNodeReference(string $file_path, PhpParser\Node $node, string $reference): void { if (!$reference) { diff --git a/tests/LanguageServer/CompletionTest.php b/tests/LanguageServer/CompletionTest.php index cf970eaf5..3b5a80d49 100644 --- a/tests/LanguageServer/CompletionTest.php +++ b/tests/LanguageServer/CompletionTest.php @@ -766,4 +766,36 @@ class CompletionTest extends \Psalm\Tests\TestCase $this->assertCount(2, $completion_items); } + + public function testCompletionOnClassReference(): void + { + + $codebase = $this->project_analyzer->getCodebase(); + $config = $codebase->config; + $config->throw_exception = false; + + $this->addFile( + 'somefile.php', + 'file_provider->openFile('somefile.php'); + $codebase->scanFiles(); + $this->analyzeFile('somefile.php', new Context()); + + $completion_data = $codebase->getCompletionDataAtPosition('somefile.php', new Position(8, 23)); + + $this->assertSame(['Bar\Alpha', '::', 221], $completion_data); + + $completion_items = $codebase->getCompletionItemsForClassishThing($completion_data[0], $completion_data[1]); + $this->assertCount(2, $completion_items); + } }