Skip to content

Commit f2736c9

Browse files
bors[bot]Veykril
andauthored
Merge #9663
9663: fix: Don't offer extract_variable assist when there is no surrounding block r=Veykril a=Veykril Fixes #9143 bors r+ Co-authored-by: Lukas Wirth <[email protected]>
2 parents 06b0cbf + 9279c1c commit f2736c9

File tree

1 file changed

+43
-28
lines changed

1 file changed

+43
-28
lines changed

crates/ide_assists/src/handlers/extract_variable.rs

Lines changed: 43 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,10 @@ pub(crate) fn extract_variable(acc: &mut Assists, ctx: &AssistContext) -> Option
3535
cov_mark::hit!(extract_var_in_comment_is_not_applicable);
3636
return None;
3737
}
38-
let to_extract = node.ancestors().find_map(valid_target_expr)?;
38+
let to_extract = node
39+
.ancestors()
40+
.take_while(|it| it.text_range().contains_range(ctx.frange.range))
41+
.find_map(valid_target_expr)?;
3942
if let Some(ty) = ctx.sema.type_of_expr(&to_extract) {
4043
if ty.is_unit() {
4144
return None;
@@ -142,41 +145,43 @@ enum Anchor {
142145

143146
impl Anchor {
144147
fn from(to_extract: &ast::Expr) -> Option<Anchor> {
145-
to_extract.syntax().ancestors().find_map(|node| {
146-
if let Some(expr) =
147-
node.parent().and_then(ast::BlockExpr::cast).and_then(|it| it.tail_expr())
148-
{
149-
if expr.syntax() == &node {
150-
cov_mark::hit!(test_extract_var_last_expr);
151-
return Some(Anchor::Before(node));
148+
to_extract.syntax().ancestors().take_while(|it| !ast::Item::can_cast(it.kind())).find_map(
149+
|node| {
150+
if let Some(expr) =
151+
node.parent().and_then(ast::BlockExpr::cast).and_then(|it| it.tail_expr())
152+
{
153+
if expr.syntax() == &node {
154+
cov_mark::hit!(test_extract_var_last_expr);
155+
return Some(Anchor::Before(node));
156+
}
152157
}
153-
}
154158

155-
if let Some(parent) = node.parent() {
156-
if parent.kind() == CLOSURE_EXPR {
157-
cov_mark::hit!(test_extract_var_in_closure_no_block);
158-
return Some(Anchor::WrapInBlock(node));
159-
}
160-
if parent.kind() == MATCH_ARM {
161-
if node.kind() == MATCH_GUARD {
162-
cov_mark::hit!(test_extract_var_in_match_guard);
163-
} else {
164-
cov_mark::hit!(test_extract_var_in_match_arm_no_block);
159+
if let Some(parent) = node.parent() {
160+
if parent.kind() == CLOSURE_EXPR {
161+
cov_mark::hit!(test_extract_var_in_closure_no_block);
165162
return Some(Anchor::WrapInBlock(node));
166163
}
164+
if parent.kind() == MATCH_ARM {
165+
if node.kind() == MATCH_GUARD {
166+
cov_mark::hit!(test_extract_var_in_match_guard);
167+
} else {
168+
cov_mark::hit!(test_extract_var_in_match_arm_no_block);
169+
return Some(Anchor::WrapInBlock(node));
170+
}
171+
}
167172
}
168-
}
169173

170-
if let Some(stmt) = ast::Stmt::cast(node.clone()) {
171-
if let ast::Stmt::ExprStmt(stmt) = stmt {
172-
if stmt.expr().as_ref() == Some(to_extract) {
173-
return Some(Anchor::Replace(stmt));
174+
if let Some(stmt) = ast::Stmt::cast(node.clone()) {
175+
if let ast::Stmt::ExprStmt(stmt) = stmt {
176+
if stmt.expr().as_ref() == Some(to_extract) {
177+
return Some(Anchor::Replace(stmt));
178+
}
174179
}
180+
return Some(Anchor::Before(node));
175181
}
176-
return Some(Anchor::Before(node));
177-
}
178-
None
179-
})
182+
None
183+
},
184+
)
180185
}
181186

182187
fn syntax(&self) -> &SyntaxNode {
@@ -844,4 +849,14 @@ fn main() {
844849
"2 + 2",
845850
);
846851
}
852+
853+
#[test]
854+
fn extract_var_no_block_body() {
855+
check_assist_not_applicable(
856+
extract_variable,
857+
r"
858+
const X: usize = $0100$0;
859+
",
860+
);
861+
}
847862
}

0 commit comments

Comments
 (0)