Skip to content

Commit 38d388d

Browse files
Brooooooklynclaude
andcommitted
fix: account for non-Angular decorators when inserting decls_before_class
When a class has non-Angular decorators (e.g., @log), the const declarations (_c0, etc.) were inserted between the decorator and the class statement, producing invalid syntax. Now checks decorator span positions to insert before any preceding decorators. Vite/Rolldown's built-in oxc_transformer handles the TS-to-JS conversion (type stripping, decorator lowering) downstream, so no additional transform step is needed in the Angular compiler. Also adds a custom decorator to the playground for testing. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
1 parent 55ab818 commit 38d388d

File tree

3 files changed

+19
-1
lines changed

3 files changed

+19
-1
lines changed

crates/oxc_angular_compiler/src/component/transform.rs

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1313,7 +1313,16 @@ pub fn transform_angular_file(
13131313
if let Some(id) = &class.id {
13141314
let name = id.name.to_string();
13151315
if class_definitions.contains_key(&name) {
1316-
class_positions.push((name, stmt_start, class.body.span.end));
1316+
// Account for non-Angular decorators that precede the class.
1317+
// Decorators like @Log(...) appear before `export class` in source,
1318+
// so we must insert decls_before_class before those decorators.
1319+
let effective_start = class
1320+
.decorators
1321+
.iter()
1322+
.map(|d| d.span.start)
1323+
.min()
1324+
.map_or(stmt_start, |dec_start| dec_start.min(stmt_start));
1325+
class_positions.push((name, effective_start, class.body.span.end));
13171326
}
13181327
}
13191328
}

napi/playground/src/app/app.component.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
import { Component, signal } from '@angular/core'
22
import { RouterOutlet } from '@angular/router'
33

4+
import { Log } from './custom-decorator'
5+
6+
@Log('App component loaded')
47
@Component({
58
selector: 'app-root',
69
imports: [RouterOutlet],
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
export function Log(message: string) {
2+
return function <T extends new (...args: any[]) => any>(target: T): T {
3+
console.log(message)
4+
return target
5+
}
6+
}

0 commit comments

Comments
 (0)