Skip to content

Commit 4cacedd

Browse files
bors[bot]matklad
andauthored
Merge #4810
4810: Simplify unwrapping of blocks r=matklad a=matklad bors r+ 🤖 Co-authored-by: Aleksey Kladov <aleksey.kladov@gmail.com>
2 parents 6f0cc91 + 5233766 commit 4cacedd

File tree

1 file changed

+49
-79
lines changed

1 file changed

+49
-79
lines changed

crates/ra_assists/src/handlers/unwrap_block.rs

Lines changed: 49 additions & 79 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,5 @@
11
use ra_fmt::unwrap_trivial_block;
2-
use ra_syntax::{
3-
ast::{self, ElseBranch, Expr, LoopBodyOwner},
4-
match_ast, AstNode, TextRange, T,
5-
};
2+
use ra_syntax::{ast, AstNode, TextRange, T};
63

74
use crate::{AssistContext, AssistId, Assists};
85

@@ -29,89 +26,62 @@ pub(crate) fn unwrap_block(acc: &mut Assists, ctx: &AssistContext) -> Option<()>
2926
let parent = block.syntax().parent()?;
3027
let assist_id = AssistId("unwrap_block");
3128
let assist_label = "Unwrap block";
32-
33-
let (expr, expr_to_unwrap) = match_ast! {
34-
match parent {
35-
ast::ForExpr(for_expr) => {
36-
let block_expr = for_expr.loop_body()?;
37-
let expr_to_unwrap = extract_expr(ctx.frange.range, block_expr)?;
38-
(ast::Expr::ForExpr(for_expr), expr_to_unwrap)
39-
},
40-
ast::WhileExpr(while_expr) => {
41-
let block_expr = while_expr.loop_body()?;
42-
let expr_to_unwrap = extract_expr(ctx.frange.range, block_expr)?;
43-
(ast::Expr::WhileExpr(while_expr), expr_to_unwrap)
44-
},
45-
ast::LoopExpr(loop_expr) => {
46-
let block_expr = loop_expr.loop_body()?;
47-
let expr_to_unwrap = extract_expr(ctx.frange.range, block_expr)?;
48-
(ast::Expr::LoopExpr(loop_expr), expr_to_unwrap)
49-
},
50-
ast::IfExpr(if_expr) => {
51-
let mut resp = None;
52-
53-
let then_branch = if_expr.then_branch()?;
54-
if then_branch.l_curly_token()?.text_range().contains_range(ctx.frange.range) {
55-
if let Some(ancestor) = if_expr.syntax().parent().and_then(ast::IfExpr::cast) {
56-
// For `else if` blocks
57-
let ancestor_then_branch = ancestor.then_branch()?;
58-
let l_curly_token = then_branch.l_curly_token()?;
59-
60-
let target = then_branch.syntax().text_range();
61-
return acc.add(assist_id, assist_label, target, |edit| {
62-
let range_to_del_else_if = TextRange::new(ancestor_then_branch.syntax().text_range().end(), l_curly_token.text_range().start());
63-
let range_to_del_rest = TextRange::new(then_branch.syntax().text_range().end(), if_expr.syntax().text_range().end());
64-
65-
edit.delete(range_to_del_rest);
66-
edit.delete(range_to_del_else_if);
67-
edit.replace(target, update_expr_string(then_branch.to_string(), &[' ', '{']));
68-
});
69-
} else {
70-
resp = Some((ast::Expr::IfExpr(if_expr.clone()), Expr::BlockExpr(then_branch)));
71-
}
72-
} else if let Some(else_branch) = if_expr.else_branch() {
73-
match else_branch {
74-
ElseBranch::Block(else_block) => {
75-
let l_curly_token = else_block.l_curly_token()?;
76-
if l_curly_token.text_range().contains_range(ctx.frange.range) {
77-
let target = else_block.syntax().text_range();
78-
return acc.add(assist_id, assist_label, target, |edit| {
79-
let range_to_del = TextRange::new(then_branch.syntax().text_range().end(), l_curly_token.text_range().start());
80-
81-
edit.delete(range_to_del);
82-
edit.replace(target, update_expr_string(else_block.to_string(), &[' ', '{']));
83-
});
84-
}
85-
},
86-
ElseBranch::IfExpr(_) => {},
87-
}
29+
let parent = ast::Expr::cast(parent)?;
30+
31+
match parent.clone() {
32+
ast::Expr::ForExpr(_) | ast::Expr::WhileExpr(_) | ast::Expr::LoopExpr(_) => (),
33+
ast::Expr::IfExpr(if_expr) => {
34+
let then_branch = if_expr.then_branch()?;
35+
if then_branch == block {
36+
if let Some(ancestor) = if_expr.syntax().parent().and_then(ast::IfExpr::cast) {
37+
// For `else if` blocks
38+
let ancestor_then_branch = ancestor.then_branch()?;
39+
40+
let target = then_branch.syntax().text_range();
41+
return acc.add(assist_id, assist_label, target, |edit| {
42+
let range_to_del_else_if = TextRange::new(
43+
ancestor_then_branch.syntax().text_range().end(),
44+
l_curly_token.text_range().start(),
45+
);
46+
let range_to_del_rest = TextRange::new(
47+
then_branch.syntax().text_range().end(),
48+
if_expr.syntax().text_range().end(),
49+
);
50+
51+
edit.delete(range_to_del_rest);
52+
edit.delete(range_to_del_else_if);
53+
edit.replace(
54+
target,
55+
update_expr_string(then_branch.to_string(), &[' ', '{']),
56+
);
57+
});
8858
}
89-
90-
resp?
91-
},
92-
_ => return None,
59+
} else {
60+
let target = block.syntax().text_range();
61+
return acc.add(assist_id, assist_label, target, |edit| {
62+
let range_to_del = TextRange::new(
63+
then_branch.syntax().text_range().end(),
64+
l_curly_token.text_range().start(),
65+
);
66+
67+
edit.delete(range_to_del);
68+
edit.replace(target, update_expr_string(block.to_string(), &[' ', '{']));
69+
});
70+
}
9371
}
72+
_ => return None,
9473
};
9574

96-
let target = expr_to_unwrap.syntax().text_range();
97-
acc.add(assist_id, assist_label, target, |edit| {
98-
edit.replace(
99-
expr.syntax().text_range(),
100-
update_expr_string(expr_to_unwrap.to_string(), &[' ', '{', '\n']),
75+
let unwrapped = unwrap_trivial_block(block);
76+
let target = unwrapped.syntax().text_range();
77+
acc.add(assist_id, assist_label, target, |builder| {
78+
builder.replace(
79+
parent.syntax().text_range(),
80+
update_expr_string(unwrapped.to_string(), &[' ', '{', '\n']),
10181
);
10282
})
10383
}
10484

105-
fn extract_expr(cursor_range: TextRange, block: ast::BlockExpr) -> Option<ast::Expr> {
106-
let cursor_in_range = block.l_curly_token()?.text_range().contains_range(cursor_range);
107-
108-
if cursor_in_range {
109-
Some(unwrap_trivial_block(block))
110-
} else {
111-
None
112-
}
113-
}
114-
11585
fn update_expr_string(expr_str: String, trim_start_pat: &[char]) -> String {
11686
let expr_string = expr_str.trim_start_matches(trim_start_pat);
11787
let mut expr_string_lines: Vec<&str> = expr_string.lines().collect();

0 commit comments

Comments
 (0)