Skip to content

Commit 0d82a2c

Browse files
Copilotjakebailey
andauthored
Fix JSDoc comment of elided import being preserved in declaration emit (#3963)
Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: jakebailey <5341706+jakebailey@users.noreply.github.com>
1 parent 10ff693 commit 0d82a2c

5 files changed

Lines changed: 171 additions & 7 deletions

File tree

internal/printer/printer.go

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5671,10 +5671,7 @@ func (p *Printer) emitDetachedComments(textRange core.TextRange) (result detache
56715671
}
56725672
}
56735673

5674-
if p.shouldWriteComment(comment) {
5675-
detachedComments = append(detachedComments, comment)
5676-
}
5677-
5674+
detachedComments = append(detachedComments, comment)
56785675
lastComment = comment
56795676
}
56805677

@@ -5687,11 +5684,21 @@ func (p *Printer) emitDetachedComments(textRange core.TextRange) (result detache
56875684
if nodeLine >= lastCommentLine+2 {
56885685
// Valid detachedComments
56895686

5690-
if len(leadingComments) > 0 && p.shouldEmitNewLineBeforeLeadingCommentOfPosition(textRange.Pos(), leadingComments[0].Pos()) {
5691-
p.writeLine()
5687+
// Filter to only comments that should be written (e.g., JSDoc-style in declaration emit)
5688+
var commentsToEmit []ast.CommentRange
5689+
for _, comment := range detachedComments {
5690+
if p.shouldWriteComment(comment) {
5691+
commentsToEmit = append(commentsToEmit, comment)
5692+
}
56925693
}
56935694

5694-
p.emitComments(detachedComments, commentSeparatorAfter)
5695+
if len(commentsToEmit) > 0 {
5696+
if p.shouldEmitNewLineBeforeLeadingCommentOfPosition(textRange.Pos(), commentsToEmit[0].Pos()) {
5697+
p.writeLine()
5698+
}
5699+
5700+
p.emitComments(commentsToEmit, commentSeparatorAfter)
5701+
}
56955702
result = detachedCommentsInfo{nodePos: textRange.Pos(), detachedCommentEndPos: core.LastOrNil(detachedComments).End()}
56965703
hasResult = true
56975704
}
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
//// [tests/cases/compiler/jsDocCommentOfElidedImportPreserved.ts] ////
2+
3+
//// [index.ts]
4+
export interface Foo {}
5+
6+
//// [main.ts]
7+
/**
8+
* Some random docs not related to foo
9+
*/
10+
/* trigger */
11+
import * as x from './index.js';
12+
export const foo = 1;
13+
14+
//// [detachedCopyright.ts]
15+
/**
16+
* Copyright header
17+
*/
18+
19+
import * as x from './index.js';
20+
export const bar = 2;
21+
22+
//// [detachedCopyrightNonJSDoc.ts]
23+
/* Non-JSDoc copyright header */
24+
25+
import * as x from './index.js';
26+
export const baz = 3;
27+
28+
29+
//// [index.js]
30+
export {};
31+
//// [main.js]
32+
export const foo = 1;
33+
//// [detachedCopyright.js]
34+
/**
35+
* Copyright header
36+
*/
37+
export const bar = 2;
38+
//// [detachedCopyrightNonJSDoc.js]
39+
/* Non-JSDoc copyright header */
40+
export const baz = 3;
41+
42+
43+
//// [index.d.ts]
44+
export interface Foo {
45+
}
46+
//// [main.d.ts]
47+
export declare const foo = 1;
48+
//// [detachedCopyright.d.ts]
49+
/**
50+
* Copyright header
51+
*/
52+
export declare const bar = 2;
53+
//// [detachedCopyrightNonJSDoc.d.ts]
54+
export declare const baz = 3;
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
//// [tests/cases/compiler/jsDocCommentOfElidedImportPreserved.ts] ////
2+
3+
=== index.ts ===
4+
export interface Foo {}
5+
>Foo : Symbol(Foo, Decl(index.ts, 0, 0))
6+
7+
=== main.ts ===
8+
/**
9+
* Some random docs not related to foo
10+
*/
11+
/* trigger */
12+
import * as x from './index.js';
13+
>x : Symbol(x, Decl(main.ts, 4, 6))
14+
15+
export const foo = 1;
16+
>foo : Symbol(foo, Decl(main.ts, 5, 12))
17+
18+
=== detachedCopyright.ts ===
19+
/**
20+
* Copyright header
21+
*/
22+
23+
import * as x from './index.js';
24+
>x : Symbol(x, Decl(detachedCopyright.ts, 4, 6))
25+
26+
export const bar = 2;
27+
>bar : Symbol(bar, Decl(detachedCopyright.ts, 5, 12))
28+
29+
=== detachedCopyrightNonJSDoc.ts ===
30+
/* Non-JSDoc copyright header */
31+
32+
import * as x from './index.js';
33+
>x : Symbol(x, Decl(detachedCopyrightNonJSDoc.ts, 2, 6))
34+
35+
export const baz = 3;
36+
>baz : Symbol(baz, Decl(detachedCopyrightNonJSDoc.ts, 3, 12))
37+
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
//// [tests/cases/compiler/jsDocCommentOfElidedImportPreserved.ts] ////
2+
3+
=== index.ts ===
4+
5+
export interface Foo {}
6+
7+
=== main.ts ===
8+
/**
9+
* Some random docs not related to foo
10+
*/
11+
/* trigger */
12+
import * as x from './index.js';
13+
>x : typeof x
14+
15+
export const foo = 1;
16+
>foo : 1
17+
>1 : 1
18+
19+
=== detachedCopyright.ts ===
20+
/**
21+
* Copyright header
22+
*/
23+
24+
import * as x from './index.js';
25+
>x : typeof x
26+
27+
export const bar = 2;
28+
>bar : 2
29+
>2 : 2
30+
31+
=== detachedCopyrightNonJSDoc.ts ===
32+
/* Non-JSDoc copyright header */
33+
34+
import * as x from './index.js';
35+
>x : typeof x
36+
37+
export const baz = 3;
38+
>baz : 3
39+
>3 : 3
40+
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
// @declaration: true
2+
3+
// @filename: index.ts
4+
export interface Foo {}
5+
6+
// @filename: main.ts
7+
/**
8+
* Some random docs not related to foo
9+
*/
10+
/* trigger */
11+
import * as x from './index.js';
12+
export const foo = 1;
13+
14+
// @filename: detachedCopyright.ts
15+
/**
16+
* Copyright header
17+
*/
18+
19+
import * as x from './index.js';
20+
export const bar = 2;
21+
22+
// @filename: detachedCopyrightNonJSDoc.ts
23+
/* Non-JSDoc copyright header */
24+
25+
import * as x from './index.js';
26+
export const baz = 3;

0 commit comments

Comments
 (0)