Skip to content

Commit

Permalink
Implement go-to-def for CT testcases
Browse files Browse the repository at this point in the history
Summary:
When in a Common Test suite, try resolving atoms to a function of arity 1 within the same module before attempting to resolve them as modules.

This enables:

* go-to-definition from the `init_per_suite`, `init_per_testcase`, `all`, `groups` to the testcase
* find-references from a testcase to find all usages of the same atom
* rename symbol for a testcase to update all occurrences of the testcase

While there could be some imprecision in case an atom is used for other purposes within a test suite, I believe this change will significantly improve ergonomics around test suites in most cases.

Reviewed By: michalmuskala

Differential Revision: D57666181

fbshipit-source-id: 2faf1a6798601c9e23af653f25cc39110d0aa534
  • Loading branch information
robertoaloi authored and facebook-github-bot committed May 22, 2024
1 parent 4e17470 commit c270dac
Show file tree
Hide file tree
Showing 6 changed files with 82 additions and 14 deletions.
1 change: 1 addition & 0 deletions crates/hir/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -141,6 +141,7 @@ pub use name::AsName;
pub use name::MacroName;
pub use name::Name;
pub use name::NameArity;
pub use sema::AtomDef;
pub use sema::CallDef;
pub use sema::DefinitionOrReference;
pub use sema::FaDef;
Expand Down
1 change: 1 addition & 0 deletions crates/hir/src/sema.rs
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ use la_arena::Idx;
use la_arena::RawIdx;

use self::find::FindForm;
pub use self::to_def::AtomDef;
pub use self::to_def::CallDef;
pub use self::to_def::DefinitionOrReference;
pub use self::to_def::FaDef;
Expand Down
24 changes: 20 additions & 4 deletions crates/hir/src/sema/to_def.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
*/

use elp_base_db::FileId;
use elp_base_db::FileKind;
use elp_syntax::ast;
use elp_syntax::ast::in_erlang_module;
use elp_syntax::match_ast;
Expand Down Expand Up @@ -66,8 +67,13 @@ impl<Definition, Reference> DefinitionOrReference<Definition, Reference> {

// ---------------------------------------------------------------------

pub enum AtomDef {
Module(Module),
Function(FunctionDef),
}

impl ToDef for ast::Atom {
type Def = Module;
type Def = AtomDef;

fn to_def(sema: &Semantic<'_>, ast: InFile<&Self>) -> Option<Self::Def> {
let (body, body_map) = sema.find_body_and_map(ast.file_id, ast.value.syntax())?;
Expand All @@ -82,9 +88,9 @@ impl ToDef for ast::Atom {
_ => return None,
};
let name = sema.db.lookup_atom(*atom);
let def = resolve_module_name(sema, file_id, &name)?;

Some(def)
resolve_testcase(sema, file_id, &name)
.map(AtomDef::Function)
.or_else(|| resolve_module_name(sema, file_id, &name).map(AtomDef::Module))
}
}

Expand Down Expand Up @@ -629,6 +635,16 @@ fn resolve_record(
))
}

fn resolve_testcase(sema: &Semantic<'_>, file_id: FileId, name: &Name) -> Option<FunctionDef> {
if sema.db.file_kind(file_id) != FileKind::TestModule {
return None;
}
sema.db
.def_map(file_id)
.get_function(&NameArity::new(name.clone(), 1))
.cloned()
}

// ---------------------------------------------------------------------

impl ToDef for ast::ModuleAttribute {
Expand Down
36 changes: 36 additions & 0 deletions crates/ide/src/handlers/goto_definition.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3632,4 +3632,40 @@ foo() ->
"#,
)
}

#[test]
fn testcase_from_groups() {
check(
r#"
//- /test/main_SUITE.erl
-module(main_SUITE).
-export([all/0, groups/0]).
all() -> [{group, [], my_group}].
groups() -> [{my_group, [], [my_tes~tcase]}].
my_testcase(_Config) ->
%% ^^^^^^^^^^^
ok.
//- /src/my_testcase.erl
-module(my_testcase).
"#,
)
}

#[test]
fn module_from_groups() {
check(
r#"
//- /test/main_SUITE.erl
-module(main_SUITE).
-export([all/0, groups/0]).
all() -> [{group, [], my_group}].
groups() -> [{my_group, [], [my_tes~tcase]}].
//- /src/my_testcase.erl
-module(my_testcase).
%% ^^^^^^^^^^^^^^^^^^^^^
"#,
)
}
}
24 changes: 14 additions & 10 deletions crates/ide_completion/src/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ use elp_syntax::algo;
use elp_syntax::ast;
use elp_syntax::ast::Atom;
use elp_syntax::AstNode;
use hir::AtomDef;
use hir::InFile;
use hir::NameArity;

Expand Down Expand Up @@ -61,16 +62,19 @@ fn complete_remote_name(
Some(':') | None => (),
_ => return None,
};
let module = sema.to_def(InFile::new(file_position.file_id, module_atom))?;
let def_map = sema.def_map(module.file.file_id);

let completions = def_map
.get_exported_types()
.iter()
.filter(|na| na.name().starts_with(fun_prefix))
.map(create_call_completion);
acc.extend(completions);
Some(())
match sema.to_def(InFile::new(file_position.file_id, module_atom)) {
Some(AtomDef::Module(module)) => {
let def_map = sema.def_map(module.file.file_id);
let completions = def_map
.get_exported_types()
.iter()
.filter(|na| na.name().starts_with(fun_prefix))
.map(create_call_completion);
acc.extend(completions);
Some(())
}
_ => None,
}
}

pub(crate) fn add_local(
Expand Down
10 changes: 10 additions & 0 deletions crates/ide_db/src/defs.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ use hir::db::DefDatabase;
use hir::known;
use hir::AnyExprRef;
use hir::AsName;
use hir::AtomDef;
use hir::CallDef;
use hir::CallTarget;
use hir::CallbackDef;
Expand Down Expand Up @@ -348,6 +349,15 @@ impl From<FaDef> for SymbolDefinition {
}
}

impl From<AtomDef> for SymbolDefinition {
fn from(it: AtomDef) -> Self {
match it {
AtomDef::Module(module) => module.into(),
AtomDef::Function(function) => function.into(),
}
}
}

impl From<CallDef> for SymbolDefinition {
fn from(it: CallDef) -> Self {
match it {
Expand Down

0 comments on commit c270dac

Please sign in to comment.