From 47464e556c160ce705c2e3c84f501ad4e8dbb123 Mon Sep 17 00:00:00 2001 From: Kirill Bulatov Date: Tue, 1 Dec 2020 22:46:06 +0200 Subject: [PATCH] Properly fill client completion resolve capabilities data --- crates/completion/src/config.rs | 10 ++++++++ crates/completion/src/lib.rs | 2 +- crates/ide/src/lib.rs | 4 +-- crates/rust-analyzer/src/caps.rs | 41 +++++++++++++++++++++++++++++- crates/rust-analyzer/src/config.rs | 4 ++- 5 files changed, 56 insertions(+), 5 deletions(-) diff --git a/crates/completion/src/config.rs b/crates/completion/src/config.rs index 654a76f7b33..736af455ef0 100644 --- a/crates/completion/src/config.rs +++ b/crates/completion/src/config.rs @@ -5,6 +5,7 @@ //! completions if we are allowed to. use ide_db::helpers::insert_use::MergeBehaviour; +use rustc_hash::FxHashSet; #[derive(Clone, Debug, PartialEq, Eq)] pub struct CompletionConfig { @@ -14,6 +15,14 @@ pub struct CompletionConfig { pub add_call_argument_snippets: bool, pub snippet_cap: Option, pub merge: Option, + pub resolve_capabilities: FxHashSet, +} + +#[derive(Debug, Copy, Clone, Hash, Eq, PartialEq)] +pub enum CompletionResolveCapability { + Documentation, + Detail, + AdditionalTextEdits, } impl CompletionConfig { @@ -36,6 +45,7 @@ fn default() -> Self { add_call_argument_snippets: true, snippet_cap: Some(SnippetCap { _private: () }), merge: Some(MergeBehaviour::Full), + resolve_capabilities: FxHashSet::default(), } } } diff --git a/crates/completion/src/lib.rs b/crates/completion/src/lib.rs index 28209d4e0a9..c689b0ddee5 100644 --- a/crates/completion/src/lib.rs +++ b/crates/completion/src/lib.rs @@ -17,7 +17,7 @@ use crate::{completions::Completions, context::CompletionContext, item::CompletionKind}; pub use crate::{ - config::CompletionConfig, + config::{CompletionConfig, CompletionResolveCapability}, item::{CompletionItem, CompletionItemKind, CompletionScore, ImportToAdd, InsertTextFormat}, }; diff --git a/crates/ide/src/lib.rs b/crates/ide/src/lib.rs index 7015a512680..d1a27f3a599 100644 --- a/crates/ide/src/lib.rs +++ b/crates/ide/src/lib.rs @@ -80,8 +80,8 @@ macro_rules! eprintln { }, }; pub use completion::{ - CompletionConfig, CompletionItem, CompletionItemKind, CompletionScore, ImportToAdd, - InsertTextFormat, + CompletionConfig, CompletionItem, CompletionItemKind, CompletionResolveCapability, + CompletionScore, ImportToAdd, InsertTextFormat, }; pub use ide_db::{ call_info::CallInfo, diff --git a/crates/rust-analyzer/src/caps.rs b/crates/rust-analyzer/src/caps.rs index c559e1a3d6f..d6b862088b2 100644 --- a/crates/rust-analyzer/src/caps.rs +++ b/crates/rust-analyzer/src/caps.rs @@ -1,6 +1,7 @@ //! Advertizes the capabilities of the LSP Server. use std::env; +use ide::CompletionResolveCapability; use lsp_types::{ CallHierarchyServerCapability, ClientCapabilities, CodeActionKind, CodeActionOptions, CodeActionProviderCapability, CodeLensOptions, CompletionOptions, @@ -11,6 +12,7 @@ TextDocumentSyncKind, TextDocumentSyncOptions, TypeDefinitionProviderCapability, WorkDoneProgressOptions, }; +use rustc_hash::FxHashSet; use serde_json::json; use crate::semantic_tokens; @@ -48,7 +50,9 @@ pub fn server_capabilities(client_caps: &ClientCapabilities) -> ServerCapabiliti document_symbol_provider: Some(OneOf::Left(true)), workspace_symbol_provider: Some(OneOf::Left(true)), code_action_provider: Some(code_action_capabilities(client_caps)), - code_lens_provider: Some(CodeLensOptions { resolve_provider: Some(true) }), + code_lens_provider: Some(CodeLensOptions { + resolve_provider: resolve_provider(client_caps), + }), document_formatting_provider: Some(OneOf::Left(true)), document_range_formatting_provider: None, document_on_type_formatting_provider: Some(DocumentOnTypeFormattingOptions { @@ -93,6 +97,41 @@ pub fn server_capabilities(client_caps: &ClientCapabilities) -> ServerCapabiliti } } +fn resolve_provider(client_caps: &ClientCapabilities) -> Option { + if enabled_resolve_capabilities(client_caps)?.is_empty() { + None + } else { + Some(true) + } +} + +/// Parses client capabilities and returns all that rust-analyzer supports. +pub fn enabled_resolve_capabilities( + caps: &ClientCapabilities, +) -> Option> { + Some( + caps.text_document + .as_ref()? + .completion + .as_ref()? + .completion_item + .as_ref()? + .resolve_support + .as_ref()? + .properties + .iter() + .filter_map(|cap_string| { + Some(match cap_string.as_str() { + "additionalTextEdits" => CompletionResolveCapability::AdditionalTextEdits, + "detail" => CompletionResolveCapability::Detail, + "documentation" => CompletionResolveCapability::Documentation, + _unsupported => return None, + }) + }) + .collect(), + ) +} + fn code_action_capabilities(client_caps: &ClientCapabilities) -> CodeActionProviderCapability { client_caps .text_document diff --git a/crates/rust-analyzer/src/config.rs b/crates/rust-analyzer/src/config.rs index 59269a74b91..83f09782969 100644 --- a/crates/rust-analyzer/src/config.rs +++ b/crates/rust-analyzer/src/config.rs @@ -19,7 +19,7 @@ use serde::Deserialize; use vfs::AbsPathBuf; -use crate::diagnostics::DiagnosticsMapConfig; +use crate::{caps::enabled_resolve_capabilities, diagnostics::DiagnosticsMapConfig}; #[derive(Debug, Clone)] pub struct Config { @@ -388,6 +388,8 @@ pub fn update_caps(&mut self, caps: &ClientCapabilities) { } self.completion.allow_snippets(false); + self.completion.resolve_capabilities = + enabled_resolve_capabilities(caps).unwrap_or_default(); if let Some(completion) = &doc_caps.completion { if let Some(completion_item) = &completion.completion_item { if let Some(value) = completion_item.snippet_support { -- 2.44.0