Skip to content

Commit

Permalink
Fix #5295 - offer static methods for completion too in instance mode
Browse files Browse the repository at this point in the history
  • Loading branch information
muglug committed Feb 27, 2021
1 parent 44f8d71 commit 7db742d
Show file tree
Hide file tree
Showing 2 changed files with 68 additions and 46 deletions.
77 changes: 32 additions & 45 deletions src/Psalm/Codebase.php
Original file line number Diff line number Diff line change
Expand Up @@ -1467,8 +1467,7 @@ public function getTypeContextAtPosition(string $file_path, Position $position):
*/
public function getCompletionItemsForClassishThing(string $type_string, string $gap) : array
{
$instance_completion_items = [];
$static_completion_items = [];
$completion_items = [];

$type = Type::parseString($type_string);

Expand All @@ -1480,24 +1479,25 @@ public function getCompletionItemsForClassishThing(string $type_string, string $
foreach ($class_storage->appearing_method_ids as $declaring_method_id) {
$method_storage = $this->methods->getStorage($declaring_method_id);

$completion_item = new \LanguageServerProtocol\CompletionItem(
$method_storage->cased_name,
\LanguageServerProtocol\CompletionItemKind::METHOD,
(string)$method_storage,
$method_storage->description,
(string)$method_storage->visibility,
$method_storage->cased_name,
$method_storage->cased_name . (count($method_storage->params) !== 0 ? '($0)' : '()'),
null,
null,
new Command('Trigger parameter hints', 'editor.action.triggerParameterHints')
);
$completion_item->insertTextFormat = \LanguageServerProtocol\InsertTextFormat::SNIPPET;

if ($method_storage->is_static) {
$static_completion_items[] = $completion_item;
} else {
$instance_completion_items[] = $completion_item;
if ($method_storage->is_static || $gap === '->') {
$completion_item = new \LanguageServerProtocol\CompletionItem(
$method_storage->cased_name,
\LanguageServerProtocol\CompletionItemKind::METHOD,
(string)$method_storage,
$method_storage->description,
(string)$method_storage->visibility,
$method_storage->cased_name,
$method_storage->cased_name . (count($method_storage->params) !== 0 ? '($0)' : '()'),
null,
null,
new Command('Trigger parameter hints', 'editor.action.triggerParameterHints'),
null,
2
);

$completion_item->insertTextFormat = \LanguageServerProtocol\InsertTextFormat::SNIPPET;

$completion_items[] = $completion_item;
}
}

Expand All @@ -1506,25 +1506,21 @@ public function getCompletionItemsForClassishThing(string $type_string, string $
$declaring_class . '::$' . $property_name
);

$completion_item = new \LanguageServerProtocol\CompletionItem(
'$' . $property_name,
\LanguageServerProtocol\CompletionItemKind::PROPERTY,
$property_storage->getInfo(),
$property_storage->description,
(string)$property_storage->visibility,
$property_name,
($gap === '::' ? '$' : '') . $property_name
);

if ($property_storage->is_static) {
$static_completion_items[] = $completion_item;
} else {
$instance_completion_items[] = $completion_item;
if ($property_storage->is_static || $gap === '->') {
$completion_items[] = new \LanguageServerProtocol\CompletionItem(
'$' . $property_name,
\LanguageServerProtocol\CompletionItemKind::PROPERTY,
$property_storage->getInfo(),
$property_storage->description,
(string)$property_storage->visibility,
$property_name,
($gap === '::' ? '$' : '') . $property_name
);
}
}

foreach ($class_storage->constants as $const_name => $const) {
$static_completion_items[] = new \LanguageServerProtocol\CompletionItem(
$completion_items[] = new \LanguageServerProtocol\CompletionItem(
$const_name,
\LanguageServerProtocol\CompletionItemKind::VARIABLE,
'const ' . $const_name,
Expand All @@ -1541,15 +1537,6 @@ public function getCompletionItemsForClassishThing(string $type_string, string $
}
}

if ($gap === '->') {
$completion_items = $instance_completion_items;
} else {
$completion_items = array_merge(
$instance_completion_items,
$static_completion_items
);
}

return $completion_items;
}

Expand Down Expand Up @@ -1713,7 +1700,7 @@ public function getCompletionItemsForPartialSymbol(
$function_name . (count($function->params) !== 0 ? '($0)' : '()'),
null,
null,
null,
new Command('Trigger parameter hints', 'editor.action.triggerParameterHints'),
null,
2
);
Expand Down
37 changes: 36 additions & 1 deletion tests/LanguageServer/CompletionTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -1390,7 +1390,6 @@ function my_func(string $arg_a, bool $arg_b) : string {

public function testTypeContextForFunctionArgumentWithWhiteSpace(): void
{

$codebase = $this->project_analyzer->getCodebase();
$config = $codebase->config;
$config->throw_exception = false;
Expand All @@ -1413,6 +1412,42 @@ function my_func(string $arg_a, bool $arg_b) : string {
$this->assertSame('bool', (string) $type);
}

public function testCallStaticInInstance(): void
{
$codebase = $this->project_analyzer->getCodebase();
$config = $codebase->config;
$config->throw_exception = false;

$this->addFile(
'somefile.php',
'<?php
class Foo
{
public function testFoo() {
$this->
}
public static function bar() : void {}
public function baz() : void {}
}'
);

$codebase = $this->project_analyzer->getCodebase();

$codebase->file_provider->openFile('somefile.php');
$codebase->scanFiles();
$this->analyzeFile('somefile.php', new Context());

$completion_data = $codebase->getCompletionDataAtPosition('somefile.php', new Position(4, 31));

$this->assertSame(['Foo&static', '->', 129], $completion_data);

$completion_items = $codebase->getCompletionItemsForClassishThing($completion_data[0], $completion_data[1]);

$this->assertCount(3, $completion_items);
}

public function testCompletionsForType(): void
{
$codebase = $this->project_analyzer->getCodebase();
Expand Down

0 comments on commit 7db742d

Please sign in to comment.