Ensure that listing&resolving code actions use the same set of actions

This commit is contained in:
Aleksey Kladov 2021-04-13 11:27:00 +03:00
parent fe29a9e837
commit 04b5fcfdb2
2 changed files with 43 additions and 23 deletions

View file

@ -531,6 +531,34 @@ impl Analysis {
self.with_db(|db| diagnostics::diagnostics(db, config, file_id))
}
/// Convenience function to return assists + quick fixes for diagnostics
pub fn assists_with_fixes(
&self,
assist_config: &AssistConfig,
diagnostics_config: &DiagnosticsConfig,
resolve: bool,
frange: FileRange,
) -> Cancelable<Vec<Assist>> {
let include_fixes = match &assist_config.allowed {
Some(it) => it.iter().any(|&it| it == AssistKind::None || it == AssistKind::QuickFix),
None => true,
};
self.with_db(|db| {
let mut res = Assist::get(db, assist_config, resolve, frange);
ssr::add_ssr_assist(db, &mut res, resolve, frange);
if include_fixes {
res.extend(
diagnostics::diagnostics(db, diagnostics_config, frange.file_id)
.into_iter()
.filter_map(|it| it.fix),
);
}
res
})
}
/// Returns the edit required to rename reference at the position to the new
/// name.
pub fn rename(

View file

@ -8,8 +8,8 @@ use std::{
};
use ide::{
AnnotationConfig, AssistKind, FileId, FilePosition, FileRange, HoverAction, HoverGotoTypeData,
Query, RangeInfo, Runnable, RunnableKind, SearchScope, SourceChange, TextEdit,
AnnotationConfig, FileId, FilePosition, FileRange, HoverAction, HoverGotoTypeData, Query,
RangeInfo, Runnable, RunnableKind, SearchScope, SourceChange, TextEdit,
};
use ide_db::SymbolKind;
use itertools::Itertools;
@ -1003,27 +1003,13 @@ pub(crate) fn handle_code_action(
let mut res: Vec<lsp_ext::CodeAction> = Vec::new();
let include_quick_fixes = match &assists_config.allowed {
Some(v) => v.iter().any(|it| it == &AssistKind::None || it == &AssistKind::QuickFix),
None => true,
};
let code_action_resolve_cap = snap.config.code_action_resolve();
let mut assists = Vec::new();
// Fixes from native diagnostics.
if include_quick_fixes {
let diagnostics = snap.analysis.diagnostics(&snap.config.diagnostics(), frange.file_id)?;
assists.extend(
diagnostics
.into_iter()
.filter_map(|d| d.fix)
.filter(|fix| fix.target.intersect(frange.range).is_some()),
)
}
// Assists proper.
assists.extend(snap.analysis.assists(&assists_config, !code_action_resolve_cap, frange)?);
let assists = snap.analysis.assists_with_fixes(
&assists_config,
&snap.config.diagnostics(),
!code_action_resolve_cap,
frange,
)?;
for (index, assist) in assists.into_iter().enumerate() {
let resolve_data =
if code_action_resolve_cap { Some((index, params.clone())) } else { None };
@ -1066,7 +1052,13 @@ pub(crate) fn handle_code_action_resolve(
.only
.map(|it| it.into_iter().filter_map(from_proto::assist_kind).collect());
let assists = snap.analysis.assists(&assists_config, true, frange)?;
let assists = snap.analysis.assists_with_fixes(
&assists_config,
&snap.config.diagnostics(),
true,
frange,
)?;
let (id, index) = split_once(&params.id, ':').unwrap();
let index = index.parse::<usize>().unwrap();
let assist = &assists[index];