Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 16 additions & 0 deletions crates/oxc_codegen/src/comment.rs
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,22 @@ impl Codegen<'_> {
}
}

/// Print comments attached to any position in the given range `(start, end)` (exclusive).
/// Returns `true` if any comments were printed.
pub(crate) fn print_comments_in_range(&mut self, start: u32, end: u32) -> bool {
if self.comments.is_empty() {
return false;
}
// Find and remove the first key in the range.
let key = self.comments.keys().find(|&&k| k > start && k < end).copied();
if let Some(key) = key {
let comments = self.comments.remove(&key).unwrap();
self.print_comments(&comments);
return true;
}
false
}

pub(crate) fn print_expr_comments(&mut self, start: u32) -> bool {
if self.comments.is_empty() {
return false;
Expand Down
19 changes: 15 additions & 4 deletions crates/oxc_codegen/src/gen.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2482,9 +2482,16 @@ impl Gen for JSXEmptyExpression {

impl Gen for JSXExpression<'_> {
fn r#gen(&self, p: &mut Codegen, ctx: Context) {
match self {
Self::EmptyExpression(expr) => expr.print(p, ctx),
_ => p.print_expression(self.to_expression()),
if let Self::EmptyExpression(expr) = self {
expr.print(p, ctx);
} else {
let expr = self.to_expression();
let start = expr.span().start;
if p.has_comment(start) {
p.print_comments_at(start);
p.print_indent();
}
p.print_expression(expr);
}
}
}
Expand Down Expand Up @@ -2515,7 +2522,11 @@ impl Gen for JSXAttributeValue<'_> {

impl Gen for JSXSpreadAttribute<'_> {
fn r#gen(&self, p: &mut Codegen, _ctx: Context) {
p.print_str("{...");
p.print_ascii_byte(b'{');
if p.print_comments_in_range(self.span.start, self.argument.span().start) {
p.print_indent();
}
p.print_str("...");
self.argument.print_expr(p, Precedence::Comma, Context::empty());
p.print_ascii_byte(b'}');
}
Expand Down
10 changes: 10 additions & 0 deletions crates/oxc_codegen/tests/integration/comments.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,16 @@ fn test_comment_at_top_of_file() {
#[test]
fn unit() {
test_same("<div>{/* Hello */}</div>;\n");
// https://github.com/oxc-project/oxc/issues/17266
test("console.log(<div x={/*before*/ x} />)", "console.log(<div x={/*before*/ x} />);\n");
test(
"console.log(<div x={/*before*/ \"y\"} />)",
"console.log(<div x={/*before*/ \"y\"} />);\n",
);
test("console.log(<div x={/*before*/ true} />)", "console.log(<div x={/*before*/ true} />);\n");
test("console.log(<div {/*before*/ ...x} />)", "console.log(<div {/*before*/ ...x} />);\n");
test("console.log(<div>{/*before*/ x}</div>)", "console.log(<div>{/*before*/ x}</div>);\n");
test("console.log(<>{/*before*/ x}</>)", "console.log(<>{/*before*/ x}</>);\n");
// https://lingui.dev/ref/macro#definemessage
test("const message = /*i18n*/{};", "const message = (/*i18n*/ {});\n");
test(
Expand Down
Loading