]> git.lizzy.rs Git - rust.git/commitdiff
Merge #7958
authorbors[bot] <26634292+bors[bot]@users.noreply.github.com>
Wed, 10 Mar 2021 15:07:46 +0000 (15:07 +0000)
committerGitHub <noreply@github.com>
Wed, 10 Mar 2021 15:07:46 +0000 (15:07 +0000)
7958: Avoid double text edits when renaming mod declaration r=matklad a=Veykril

Closes https://github.com/rust-analyzer/rust-analyzer/issues/7916

See https://github.com/microsoft/vscode-languageserver-node/issues/752 for context

Co-authored-by: Lukas Wirth <lukastw97@gmail.com>
crates/hir/src/lib.rs
crates/ide/src/references/rename.rs
crates/rust-analyzer/src/config.rs
crates/rust-analyzer/src/handlers.rs

index 4ef38c0f0d605f7ce21fa1351ff2bea5a71bba7c..58adc8fd386cb25215189f22d6aad32e4a630b29 100644 (file)
@@ -305,7 +305,6 @@ pub fn name(self, db: &dyn HirDatabase) -> Option<Name> {
             ModuleDef::Module(it) => it.name(db),
             ModuleDef::Const(it) => it.name(db),
             ModuleDef::Static(it) => it.name(db),
-
             ModuleDef::BuiltinType(it) => Some(it.name()),
         }
     }
index 05c73de88f7d513222cf9518ef56071a8d8630d0..bb68bcc78d47e47d8c0ded51a7785ad4b0ab8eb6 100644 (file)
@@ -94,6 +94,7 @@ pub(crate) fn rename_with_semantics(
     }
 }
 
+/// Called by the client when it is about to rename a file.
 pub(crate) fn will_rename_file(
     db: &RootDatabase,
     file_id: FileId,
index 25df1355460529f173e46e5a0fe841c0bc158ca1..8af7871ac49f7adb8d9d70721827067a0a8171df 100644 (file)
@@ -395,6 +395,9 @@ pub fn code_action_literals(&self) -> bool {
     pub fn work_done_progress(&self) -> bool {
         try_or!(self.caps.window.as_ref()?.work_done_progress?, false)
     }
+    pub fn will_rename(&self) -> bool {
+        try_or!(self.caps.workspace.as_ref()?.file_operations.as_ref()?.will_rename?, false)
+    }
     pub fn code_action_resolve(&self) -> bool {
         try_or!(
             self.caps
index b5b2ffe500f354ab8f2cfed1ec869aa8c746409c..6cc433cb81b7c2b3c603fbbb194db6984051e0cd 100644 (file)
@@ -799,8 +799,18 @@ pub(crate) fn handle_rename(
     let _p = profile::span("handle_rename");
     let position = from_proto::file_position(&snap, params.text_document_position)?;
 
-    let change =
+    let mut change =
         snap.analysis.rename(position, &*params.new_name)?.map_err(to_proto::rename_error)?;
+
+    // this is kind of a hack to prevent double edits from happening when moving files
+    // When a module gets renamed by renaming the mod declaration this causes the file to move
+    // which in turn will trigger a WillRenameFiles request to the server for which we reply with a
+    // a second identical set of renames, the client will then apply both edits causing incorrect edits
+    // with this we only emit source_file_edits in the WillRenameFiles response which will do the rename instead
+    // See https://github.com/microsoft/vscode-languageserver-node/issues/752 for more info
+    if !change.file_system_edits.is_empty() && snap.config.will_rename() {
+        change.source_file_edits.clear();
+    }
     let workspace_edit = to_proto::workspace_edit(&snap, change)?;
     Ok(Some(workspace_edit))
 }