Skip to content

Commit f9b0875

Browse files
committed
fix: #127 - Handle ASI in a single line conditionally braced body.
Closes #127.
1 parent 2aaac1e commit f9b0875

File tree

4 files changed

+62
-1
lines changed

4 files changed

+62
-1
lines changed

src/parsing/node_helpers.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -195,3 +195,11 @@ pub fn is_test_library_call_expr(node: &CallExpr, module: &Module) -> bool {
195195
pub fn is_optional_call_expr<'a>(node: &dyn NodeTrait<'a>) -> bool {
196196
return node.parent().unwrap().kind() == NodeKind::OptChainExpr;
197197
}
198+
199+
pub fn is_expr_stmt_or_body_with_single_expr_stmt<'a>(node: Node<'a>) -> bool {
200+
match node {
201+
Node::ExprStmt(_) => true,
202+
Node::BlockStmt(block) => block.stmts.len() == 1 && block.stmts[0].is::<ExprStmt>(),
203+
_ => false,
204+
}
205+
}

src/parsing/parser.rs

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3321,7 +3321,17 @@ fn parse_expr_stmt<'a>(stmt: &'a ExprStmt, context: &mut Context<'a>) -> PrintIt
33213321
let parsed_node = parsed_node.into_rc_path();
33223322
return if should_add_semi_colon(&parsed_node).unwrap_or(false) {
33233323
let mut items = PrintItems::new();
3324-
items.push_str(";");
3324+
if let Some(brace_condition_ref) = context.take_expr_stmt_single_line_parent_brace_ref() {
3325+
// Do not add a semi-colon when the semi-colon is within an if stmt or for-like stmt where
3326+
// there are no braces on the parent (ex. `if (true) []`) as this would break the code.
3327+
items.push_condition(if_true(
3328+
"semiColonIfBrace",
3329+
move |context| context.get_resolved_condition(&brace_condition_ref),
3330+
";".into(),
3331+
));
3332+
} else {
3333+
items.push_str(";");
3334+
}
33253335
items.extend(parsed_node.into());
33263336
items
33273337
} else {
@@ -6447,6 +6457,11 @@ fn parse_conditional_brace_body<'a>(opts: ParseConditionalBraceBodyOptions<'a>,
64476457
}, vec![end_info]);
64486458
let open_brace_condition_ref = open_brace_condition.get_reference();
64496459

6460+
// store the brace condition if ASI and the body is an expression statement
6461+
if context.config.semi_colons == SemiColons::Asi && node_helpers::is_expr_stmt_or_body_with_single_expr_stmt(opts.body_node) {
6462+
context.store_expr_stmt_single_line_parent_brace_ref(open_brace_condition_ref);
6463+
}
6464+
64506465
// parse body
64516466
let mut items = PrintItems::new();
64526467
items.push_info(start_info);

src/parsing/parser_types.rs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ pub struct Context<'a> {
2121
pub end_statement_or_member_infos: Stack<Info>,
2222
before_comments_start_info_stack: Stack<(Span, Info)>,
2323
if_stmt_last_brace_condition_ref: Option<ConditionReference>,
24+
expr_stmt_single_line_parent_brace_ref: Option<ConditionReference>,
2425
/// Used for ensuring nodes are parsed in order.
2526
#[cfg(debug_assertions)]
2627
pub last_parsed_node_pos: u32,
@@ -48,6 +49,7 @@ impl<'a> Context<'a> {
4849
end_statement_or_member_infos: Stack::new(),
4950
before_comments_start_info_stack: Stack::new(),
5051
if_stmt_last_brace_condition_ref: None,
52+
expr_stmt_single_line_parent_brace_ref: None,
5153
#[cfg(debug_assertions)]
5254
last_parsed_node_pos: 0,
5355
}
@@ -89,6 +91,14 @@ impl<'a> Context<'a> {
8991
self.if_stmt_last_brace_condition_ref.take()
9092
}
9193

94+
pub fn store_expr_stmt_single_line_parent_brace_ref(&mut self, condition_reference: ConditionReference) {
95+
self.expr_stmt_single_line_parent_brace_ref = Some(condition_reference);
96+
}
97+
98+
pub fn take_expr_stmt_single_line_parent_brace_ref(&mut self) -> Option<ConditionReference> {
99+
self.expr_stmt_single_line_parent_brace_ref.take()
100+
}
101+
92102
pub fn get_or_create_current_before_comments_start_info(&mut self) -> Info {
93103
let current_span = self.current_node.span();
94104
if let Some((span, info)) = self.before_comments_start_info_stack.peek() {

tests/specs/issues/issue0127.txt

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
~~ semiColons: asi, useBraces: preferNone ~~
2+
== should handle ASI in single line conditionally braced parent statements ==
3+
for (const test of asdf)
4+
[]
5+
6+
for (const test in asdf)
7+
[]
8+
9+
for (let i = 0; i < 10; i++)
10+
[]
11+
12+
if (true) []
13+
14+
while (true) []
15+
16+
[expect]
17+
for (const test of asdf)
18+
[]
19+
20+
for (const test in asdf)
21+
[]
22+
23+
for (let i = 0; i < 10; i++)
24+
[]
25+
26+
if (true) []
27+
28+
while (true) []

0 commit comments

Comments
 (0)