1
0
Fork 0

add rename functionality

pull/768/head
Florian Schunk 2019-10-11 21:30:14 +02:00
parent 9dc1656592
commit 207c6a2a68
2 changed files with 63 additions and 1 deletions

View File

@ -6,6 +6,7 @@ use LanguageServerProtocol\Location;
use LanguageServerProtocol\Position; use LanguageServerProtocol\Position;
use LanguageServerProtocol\Range; use LanguageServerProtocol\Range;
use Microsoft\PhpParser\Node; use Microsoft\PhpParser\Node;
use Microsoft\PhpParser\Token;
use Microsoft\PhpParser\PositionUtilities; use Microsoft\PhpParser\PositionUtilities;
class LocationFactory class LocationFactory
@ -29,4 +30,24 @@ class LocationFactory
new Position($range->end->line, $range->end->character) new Position($range->end->line, $range->end->character)
)); ));
} }
/**
* Returns the location of the token
*
* @param Token $node
* @return self
*/
public static function fromToken(Node $node, Token $token): Location
{
$range = PositionUtilities::getRangeFromPosition(
$token->getStartPosition(),
$token->getWidth(),
$node->getFileContents()
);
return new Location($node->getUri(), new Range(
new Position($range->start->line, $range->start->character),
new Position($range->end->line, $range->end->character)
));
}
} }

View File

@ -23,6 +23,8 @@ use LanguageServerProtocol\{
TextDocumentIdentifier, TextDocumentIdentifier,
TextDocumentItem, TextDocumentItem,
VersionedTextDocumentIdentifier, VersionedTextDocumentIdentifier,
WorkspaceEdit,
TextEdit,
CompletionContext CompletionContext
}; };
use Microsoft\PhpParser\Node; use Microsoft\PhpParser\Node;
@ -179,7 +181,7 @@ class TextDocument
TextDocumentIdentifier $textDocument, TextDocumentIdentifier $textDocument,
Position $position Position $position
): Promise { ): Promise {
return coroutine(function () use ($textDocument, $position) { return coroutine(function () use ($context, $textDocument, $position) {
$document = yield $this->documentLoader->getOrLoad($textDocument->uri); $document = yield $this->documentLoader->getOrLoad($textDocument->uri);
$node = $document->getNodeAtPosition($position); $node = $document->getNodeAtPosition($position);
if ($node === null) { if ($node === null) {
@ -211,6 +213,9 @@ class TextDocument
$descendantNode->getName() === $node->getName() $descendantNode->getName() === $node->getName()
) { ) {
$locations[] = LocationFactory::fromNode($descendantNode); $locations[] = LocationFactory::fromNode($descendantNode);
} else if (($descendantNode instanceof Node\Parameter)
&& $context->includeDeclaration && $descendantNode->getName() === $node->getName() ) {
$locations[] = LocationFactory::fromToken($descendantNode, $descendantNode->variableName);
} }
} }
} else { } else {
@ -245,6 +250,42 @@ class TextDocument
}); });
} }
/**
* The rename request is sent from the client to the server to perform a workspace-wide rename of a symbol.
*
* @param TextDocumentIdentifier $textDocument The document to rename in.
* @param Position $position The position at which this request was sent.
* @param string $newName The new name of the symbol.
* @return Promise <WorkspaceEdit|null>
*/
public function rename(
TextDocumentIdentifier $textDocument,
Position $position,
string $newName
) : Promise {
return coroutine( function () use ($textDocument, $position, $newName) {
$document = yield $this->documentLoader->getOrLoad($textDocument->uri);
$node = $document->getNodeAtPosition($position);
if (
$node instanceof Node\Expression\Variable ||
$node instanceof Node\Parameter
) {
$newName = '$' . $newName;
}
$locations = yield $this->references(new ReferenceContext(true), $textDocument, $position);
$edits = [$textDocument->uri => [] ];
foreach ($locations as $location) {
$textEdit = new TextEdit($location->range, $newName);
if (!isset($edits[$location->uri])) {
$edits[$location->uri] = [];
}
$edits[$location->uri][] = $textEdit;
}
return new WorkspaceEdit($edits);
});
}
/** /**
* The signature help request is sent from the client to the server to request signature information at a given * The signature help request is sent from the client to the server to request signature information at a given
* cursor position. * cursor position.