mirror of
https://github.com/rust-lang/rust-analyzer.git
synced 2025-09-27 04:19:13 +00:00
Treat BlockExpr as a potential module origin
This commit is contained in:
parent
7d5ed18c42
commit
82146737ac
8 changed files with 44 additions and 7 deletions
|
@ -158,11 +158,11 @@ impl FunctionBuilder {
|
||||||
it.text_range().end()
|
it.text_range().end()
|
||||||
}
|
}
|
||||||
GeneratedFunctionTarget::InEmptyItemList(it) => {
|
GeneratedFunctionTarget::InEmptyItemList(it) => {
|
||||||
let indent = IndentLevel::from_node(it.syntax());
|
let indent = IndentLevel::from_node(&it);
|
||||||
leading_ws = format!("\n{}", indent + 1);
|
leading_ws = format!("\n{}", indent + 1);
|
||||||
fn_def = fn_def.indent(indent + 1);
|
fn_def = fn_def.indent(indent + 1);
|
||||||
trailing_ws = format!("\n{}", indent);
|
trailing_ws = format!("\n{}", indent);
|
||||||
it.syntax().text_range().start() + TextSize::of('{')
|
it.text_range().start() + TextSize::of('{')
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -179,14 +179,14 @@ impl FunctionBuilder {
|
||||||
|
|
||||||
enum GeneratedFunctionTarget {
|
enum GeneratedFunctionTarget {
|
||||||
BehindItem(SyntaxNode),
|
BehindItem(SyntaxNode),
|
||||||
InEmptyItemList(ast::ItemList),
|
InEmptyItemList(SyntaxNode),
|
||||||
}
|
}
|
||||||
|
|
||||||
impl GeneratedFunctionTarget {
|
impl GeneratedFunctionTarget {
|
||||||
fn syntax(&self) -> &SyntaxNode {
|
fn syntax(&self) -> &SyntaxNode {
|
||||||
match self {
|
match self {
|
||||||
GeneratedFunctionTarget::BehindItem(it) => it,
|
GeneratedFunctionTarget::BehindItem(it) => it,
|
||||||
GeneratedFunctionTarget::InEmptyItemList(it) => it.syntax(),
|
GeneratedFunctionTarget::InEmptyItemList(it) => it,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -323,7 +323,16 @@ fn next_space_for_fn_in_module(
|
||||||
if let Some(last_item) = it.item_list().and_then(|it| it.items().last()) {
|
if let Some(last_item) = it.item_list().and_then(|it| it.items().last()) {
|
||||||
GeneratedFunctionTarget::BehindItem(last_item.syntax().clone())
|
GeneratedFunctionTarget::BehindItem(last_item.syntax().clone())
|
||||||
} else {
|
} else {
|
||||||
GeneratedFunctionTarget::InEmptyItemList(it.item_list()?)
|
GeneratedFunctionTarget::InEmptyItemList(it.item_list()?.syntax().clone())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
hir::ModuleSource::BlockExpr(it) => {
|
||||||
|
if let Some(last_item) =
|
||||||
|
it.statements().take_while(|stmt| matches!(stmt, ast::Stmt::Item(_))).last()
|
||||||
|
{
|
||||||
|
GeneratedFunctionTarget::BehindItem(last_item.syntax().clone())
|
||||||
|
} else {
|
||||||
|
GeneratedFunctionTarget::InEmptyItemList(it.syntax().clone())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -207,6 +207,7 @@ impl Attrs {
|
||||||
mod_data.definition_source(db).as_ref().map(|src| match src {
|
mod_data.definition_source(db).as_ref().map(|src| match src {
|
||||||
ModuleSource::SourceFile(file) => file as &dyn AttrsOwner,
|
ModuleSource::SourceFile(file) => file as &dyn AttrsOwner,
|
||||||
ModuleSource::Module(module) => module as &dyn AttrsOwner,
|
ModuleSource::Module(module) => module as &dyn AttrsOwner,
|
||||||
|
ModuleSource::BlockExpr(block) => block as &dyn AttrsOwner,
|
||||||
}),
|
}),
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
|
|
|
@ -109,6 +109,10 @@ pub enum ModuleOrigin {
|
||||||
Inline {
|
Inline {
|
||||||
definition: AstId<ast::Module>,
|
definition: AstId<ast::Module>,
|
||||||
},
|
},
|
||||||
|
/// Pseudo-module introduced by a block scope (contains only inner items).
|
||||||
|
BlockExpr {
|
||||||
|
block: AstId<ast::BlockExpr>,
|
||||||
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for ModuleOrigin {
|
impl Default for ModuleOrigin {
|
||||||
|
@ -122,7 +126,7 @@ impl ModuleOrigin {
|
||||||
match self {
|
match self {
|
||||||
ModuleOrigin::File { declaration: module, .. }
|
ModuleOrigin::File { declaration: module, .. }
|
||||||
| ModuleOrigin::Inline { definition: module, .. } => Some(*module),
|
| ModuleOrigin::Inline { definition: module, .. } => Some(*module),
|
||||||
ModuleOrigin::CrateRoot { .. } => None,
|
ModuleOrigin::CrateRoot { .. } | ModuleOrigin::BlockExpr { .. } => None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -137,7 +141,7 @@ impl ModuleOrigin {
|
||||||
|
|
||||||
pub fn is_inline(&self) -> bool {
|
pub fn is_inline(&self) -> bool {
|
||||||
match self {
|
match self {
|
||||||
ModuleOrigin::Inline { .. } => true,
|
ModuleOrigin::Inline { .. } | ModuleOrigin::BlockExpr { .. } => true,
|
||||||
ModuleOrigin::CrateRoot { .. } | ModuleOrigin::File { .. } => false,
|
ModuleOrigin::CrateRoot { .. } | ModuleOrigin::File { .. } => false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -155,6 +159,9 @@ impl ModuleOrigin {
|
||||||
definition.file_id,
|
definition.file_id,
|
||||||
ModuleSource::Module(definition.to_node(db.upcast())),
|
ModuleSource::Module(definition.to_node(db.upcast())),
|
||||||
),
|
),
|
||||||
|
ModuleOrigin::BlockExpr { block } => {
|
||||||
|
InFile::new(block.file_id, ModuleSource::BlockExpr(block.to_node(db.upcast())))
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -300,6 +307,7 @@ impl ModuleData {
|
||||||
pub enum ModuleSource {
|
pub enum ModuleSource {
|
||||||
SourceFile(ast::SourceFile),
|
SourceFile(ast::SourceFile),
|
||||||
Module(ast::Module),
|
Module(ast::Module),
|
||||||
|
BlockExpr(ast::BlockExpr),
|
||||||
}
|
}
|
||||||
|
|
||||||
mod diagnostics {
|
mod diagnostics {
|
||||||
|
|
|
@ -294,6 +294,7 @@ impl ToNav for hir::Module {
|
||||||
ModuleSource::Module(node) => {
|
ModuleSource::Module(node) => {
|
||||||
(node.syntax(), node.name().map(|it| it.syntax().text_range()))
|
(node.syntax(), node.name().map(|it| it.syntax().text_range()))
|
||||||
}
|
}
|
||||||
|
ModuleSource::BlockExpr(node) => (node.syntax(), None),
|
||||||
};
|
};
|
||||||
let frange = src.with_value(syntax).original_file_range(db);
|
let frange = src.with_value(syntax).original_file_range(db);
|
||||||
NavigationTarget::from_syntax(frange.file_id, name, focus, frange.range, SymbolKind::Module)
|
NavigationTarget::from_syntax(frange.file_id, name, focus, frange.range, SymbolKind::Module)
|
||||||
|
|
|
@ -53,6 +53,12 @@ impl ShortLabel for ast::SourceFile {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl ShortLabel for ast::BlockExpr {
|
||||||
|
fn short_label(&self) -> Option<String> {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl ShortLabel for ast::TypeAlias {
|
impl ShortLabel for ast::TypeAlias {
|
||||||
fn short_label(&self) -> Option<String> {
|
fn short_label(&self) -> Option<String> {
|
||||||
short_label_from_node(self, "type ")
|
short_label_from_node(self, "type ")
|
||||||
|
|
|
@ -321,6 +321,7 @@ fn hover_for_definition(db: &RootDatabase, def: Definition) -> Option<Markup> {
|
||||||
match it.definition_source(db).value {
|
match it.definition_source(db).value {
|
||||||
ModuleSource::Module(it) => it.short_label(),
|
ModuleSource::Module(it) => it.short_label(),
|
||||||
ModuleSource::SourceFile(it) => it.short_label(),
|
ModuleSource::SourceFile(it) => it.short_label(),
|
||||||
|
ModuleSource::BlockExpr(it) => it.short_label(),
|
||||||
},
|
},
|
||||||
mod_path,
|
mod_path,
|
||||||
),
|
),
|
||||||
|
|
|
@ -131,6 +131,7 @@ fn runnables_mod(sema: &Semantics<RootDatabase>, acc: &mut Vec<Runnable>, module
|
||||||
match submodule.definition_source(sema.db).value {
|
match submodule.definition_source(sema.db).value {
|
||||||
hir::ModuleSource::Module(_) => runnables_mod(sema, acc, submodule),
|
hir::ModuleSource::Module(_) => runnables_mod(sema, acc, submodule),
|
||||||
hir::ModuleSource::SourceFile(_) => mark::hit!(dont_recurse_in_outline_submodules),
|
hir::ModuleSource::SourceFile(_) => mark::hit!(dont_recurse_in_outline_submodules),
|
||||||
|
hir::ModuleSource::BlockExpr(_) => {} // inner items aren't runnable
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -228,6 +228,15 @@ impl Definition {
|
||||||
// so do nothing.
|
// so do nothing.
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
ModuleSource::BlockExpr(b) => {
|
||||||
|
if is_first {
|
||||||
|
let range = Some(b.syntax().text_range());
|
||||||
|
res.insert(file_id, range);
|
||||||
|
} else {
|
||||||
|
// We have already added the enclosing file to the search scope,
|
||||||
|
// so do nothing.
|
||||||
|
}
|
||||||
|
}
|
||||||
ModuleSource::SourceFile(_) => {
|
ModuleSource::SourceFile(_) => {
|
||||||
res.insert(file_id, None);
|
res.insert(file_id, None);
|
||||||
}
|
}
|
||||||
|
@ -257,6 +266,7 @@ impl Definition {
|
||||||
let mut res = FxHashMap::default();
|
let mut res = FxHashMap::default();
|
||||||
let range = match module_src.value {
|
let range = match module_src.value {
|
||||||
ModuleSource::Module(m) => Some(m.syntax().text_range()),
|
ModuleSource::Module(m) => Some(m.syntax().text_range()),
|
||||||
|
ModuleSource::BlockExpr(b) => Some(b.syntax().text_range()),
|
||||||
ModuleSource::SourceFile(_) => None,
|
ModuleSource::SourceFile(_) => None,
|
||||||
};
|
};
|
||||||
res.insert(file_id, range);
|
res.insert(file_id, range);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue