- self.do_update(json);
- log::info!("updated config: {:#?}", self);
- }
- fn do_update(&mut self, json: serde_json::Value) {
- let data = ConfigData::from_json(json);
-
- self.publish_diagnostics = data.diagnostics_enable;
- self.diagnostics = DiagnosticsConfig {
- disable_experimental: !data.diagnostics_enableExperimental,
- disabled: data.diagnostics_disabled,
- };
- self.diagnostics_map = DiagnosticsMapConfig {
- warnings_as_info: data.diagnostics_warningsAsInfo,
- warnings_as_hint: data.diagnostics_warningsAsHint,
- };
- self.lru_capacity = data.lruCapacity;
- self.files.watcher = match data.files_watcher.as_str() {
- "notify" => FilesWatcher::Notify,
- "client" | _ => FilesWatcher::Client,
- };
- self.notifications =
- NotificationsConfig { cargo_toml_not_found: data.notifications_cargoTomlNotFound };
- self.cargo_autoreload = data.cargo_autoreload;
-
- let rustc_source = if let Some(rustc_source) = data.rustcSource {
- let rustpath: PathBuf = rustc_source.into();
- AbsPathBuf::try_from(rustpath)
- .map_err(|_| {
- log::error!("rustc source directory must be an absolute path");
- })
- .ok()
- } else {
- None
- };
-
- self.cargo = CargoConfig {
- no_default_features: data.cargo_noDefaultFeatures,
- all_features: data.cargo_allFeatures,
- features: data.cargo_features.clone(),
- load_out_dirs_from_check: data.cargo_loadOutDirsFromCheck,
- target: data.cargo_target.clone(),
- rustc_source: rustc_source,
- no_sysroot: data.cargo_noSysroot,
- };
- self.runnables = RunnablesConfig {
- override_cargo: data.runnables_overrideCargo,
- cargo_extra_args: data.runnables_cargoExtraArgs,
- };
-
- self.proc_macro_srv = if data.procMacro_enable {
- std::env::current_exe().ok().map(|path| (path, vec!["proc-macro".into()]))
- } else {
- None
- };
-
- self.rustfmt = match data.rustfmt_overrideCommand {
- Some(mut args) if !args.is_empty() => {
- let command = args.remove(0);
- RustfmtConfig::CustomCommand { command, args }
- }
- Some(_) | None => RustfmtConfig::Rustfmt { extra_args: data.rustfmt_extraArgs },
- };
-
- self.flycheck = if data.checkOnSave_enable {
- let flycheck_config = match data.checkOnSave_overrideCommand {
- Some(mut args) if !args.is_empty() => {
- let command = args.remove(0);
- FlycheckConfig::CustomCommand { command, args }
- }
- Some(_) | None => FlycheckConfig::CargoCommand {
- command: data.checkOnSave_command,
- target_triple: data.checkOnSave_target.or(data.cargo_target),
- all_targets: data.checkOnSave_allTargets,
- no_default_features: data
- .checkOnSave_noDefaultFeatures
- .unwrap_or(data.cargo_noDefaultFeatures),
- all_features: data.checkOnSave_allFeatures.unwrap_or(data.cargo_allFeatures),
- features: data.checkOnSave_features.unwrap_or(data.cargo_features),
- extra_args: data.checkOnSave_extraArgs,
- },
- };
- Some(flycheck_config)
- } else {
- None
- };
-
- self.inlay_hints = InlayHintsConfig {
- type_hints: data.inlayHints_typeHints,
- parameter_hints: data.inlayHints_parameterHints,
- chaining_hints: data.inlayHints_chainingHints,
- max_length: data.inlayHints_maxLength,
- };
-
- self.assist.insert_use.merge = match data.assist_importMergeBehaviour {
- MergeBehaviorDef::None => None,
- MergeBehaviorDef::Full => Some(MergeBehavior::Full),
- MergeBehaviorDef::Last => Some(MergeBehavior::Last),
- };
- self.assist.insert_use.prefix_kind = match data.assist_importPrefix {
- ImportPrefixDef::Plain => PrefixKind::Plain,
- ImportPrefixDef::ByCrate => PrefixKind::ByCrate,
- ImportPrefixDef::BySelf => PrefixKind::BySelf,
- };
-
- self.completion.enable_postfix_completions = data.completion_postfix_enable;
- self.completion.enable_autoimport_completions = data.completion_autoimport_enable;
- self.completion.add_call_parenthesis = data.completion_addCallParenthesis;
- self.completion.add_call_argument_snippets = data.completion_addCallArgumentSnippets;
- self.completion.merge = self.assist.insert_use.merge;
-
- self.call_info_full = data.callInfo_full;
-
- self.lens = LensConfig {
- run: data.lens_enable && data.lens_run,
- debug: data.lens_enable && data.lens_debug,
- implementations: data.lens_enable && data.lens_implementations,
- method_refs: data.lens_enable && data.lens_methodReferences,
- };
-
- if !data.linkedProjects.is_empty() {
- self.linked_projects.clear();
- for linked_project in data.linkedProjects {
- let linked_project = match linked_project {
- ManifestOrProjectJson::Manifest(it) => {
- let path = self.root_path.join(it);
- match ProjectManifest::from_manifest_file(path) {
- Ok(it) => it.into(),
- Err(e) => {
- log::error!("failed to load linked project: {}", e);
- continue;
- }
- }
- }
- ManifestOrProjectJson::ProjectJson(it) => {
- ProjectJson::new(&self.root_path, it).into()
- }
- };
- self.linked_projects.push(linked_project);
- }
- }
-
- self.hover = HoverConfig {
- implementations: data.hoverActions_enable && data.hoverActions_implementations,
- run: data.hoverActions_enable && data.hoverActions_run,
- debug: data.hoverActions_enable && data.hoverActions_debug,
- goto_type_def: data.hoverActions_enable && data.hoverActions_gotoTypeDef,
- links_in_hover: data.hoverActions_linksInHover,
- markdown: true,
- };
- }
-
- pub fn update_caps(&mut self, caps: &ClientCapabilities) {
- self.caps = caps.clone();
- if let Some(doc_caps) = caps.text_document.as_ref() {
- if let Some(value) = doc_caps.hover.as_ref().and_then(|it| it.content_format.as_ref()) {
- self.hover.markdown = value.contains(&MarkupKind::Markdown)
- }
-
- self.completion.allow_snippets(false);
- self.completion.active_resolve_capabilities =
- enabled_completions_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 {
- self.completion.allow_snippets(value);
- }
- }
- }
- }
-
- self.assist.allow_snippets(false);
- if let Some(experimental) = &caps.experimental {
- let get_bool =
- |index: &str| experimental.get(index).and_then(|it| it.as_bool()) == Some(true);
-
- let snippet_text_edit = get_bool("snippetTextEdit");
- self.assist.allow_snippets(snippet_text_edit);
- }
-
- if let Some(workspace_caps) = caps.workspace.as_ref() {
- if let Some(refresh_support) =
- workspace_caps.semantic_tokens.as_ref().and_then(|it| it.refresh_support)
- {
- self.semantic_tokens_refresh = refresh_support;
- }
-
- if let Some(refresh_support) =
- workspace_caps.code_lens.as_ref().and_then(|it| it.refresh_support)
- {
- self.code_lens_refresh = refresh_support;
- }
- }