lsp: Add support for default rename behavior in prepareRename request (#24246)

Fixes #24184

Release Notes:

- Fixed renaming not working with some language servers (e.g. hls)
This commit is contained in:
Piotr Osiewicz 2025-02-05 13:27:57 +01:00 committed by GitHub
parent fef567bb49
commit 88b5f069fb
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 21 additions and 19 deletions

View file

@ -724,6 +724,9 @@ impl LanguageServer {
}),
rename: Some(RenameClientCapabilities {
prepare_support: Some(true),
prepare_support_default_behavior: Some(
PrepareSupportDefaultBehavior::IDENTIFIER,
),
..Default::default()
}),
hover: Some(HoverClientCapabilities {

View file

@ -299,28 +299,27 @@ impl LspCommand for PrepareRename {
_: LanguageServerId,
mut cx: AsyncApp,
) -> Result<PrepareRenameResponse> {
buffer.update(&mut cx, |buffer, _| {
match message {
Some(lsp::PrepareRenameResponse::Range(range))
| Some(lsp::PrepareRenameResponse::RangeWithPlaceholder { range, .. }) => {
let Range { start, end } = range_from_lsp(range);
if buffer.clip_point_utf16(start, Bias::Left) == start.0
&& buffer.clip_point_utf16(end, Bias::Left) == end.0
{
Ok(PrepareRenameResponse::Success(
buffer.anchor_after(start)..buffer.anchor_before(end),
))
} else {
Ok(PrepareRenameResponse::InvalidPosition)
}
}
Some(lsp::PrepareRenameResponse::DefaultBehavior { .. }) => {
Err(anyhow!("Invalid for language server to send a `defaultBehavior` response to `prepareRename`"))
}
None => {
buffer.update(&mut cx, |buffer, _| match message {
Some(lsp::PrepareRenameResponse::Range(range))
| Some(lsp::PrepareRenameResponse::RangeWithPlaceholder { range, .. }) => {
let Range { start, end } = range_from_lsp(range);
if buffer.clip_point_utf16(start, Bias::Left) == start.0
&& buffer.clip_point_utf16(end, Bias::Left) == end.0
{
Ok(PrepareRenameResponse::Success(
buffer.anchor_after(start)..buffer.anchor_before(end),
))
} else {
Ok(PrepareRenameResponse::InvalidPosition)
}
}
Some(lsp::PrepareRenameResponse::DefaultBehavior { .. }) => {
let snapshot = buffer.snapshot();
let (range, _) = snapshot.surrounding_word(self.position);
let range = snapshot.anchor_after(range.start)..snapshot.anchor_before(range.end);
Ok(PrepareRenameResponse::Success(range))
}
None => Ok(PrepareRenameResponse::InvalidPosition),
})?
}