diff --git a/internal/ast/ast.go b/internal/ast/ast.go index 57f92fbbfa..82d4f26e37 100644 --- a/internal/ast/ast.go +++ b/internal/ast/ast.go @@ -4845,6 +4845,10 @@ func IsImportDeclaration(node *Node) bool { return node.Kind == KindImportDeclaration } +func IsJSImportDeclaration(node *Node) bool { + return node.Kind == KindJSImportDeclaration +} + func IsImportDeclarationOrJSImportDeclaration(node *Node) bool { return node.Kind == KindImportDeclaration || node.Kind == KindJSImportDeclaration } diff --git a/internal/parser/parser.go b/internal/parser/parser.go index a51566f02d..7ad377c237 100644 --- a/internal/parser/parser.go +++ b/internal/parser/parser.go @@ -498,12 +498,21 @@ func (p *Parser) reparseTopLevelAwait(sourceFile *ast.SourceFile) *ast.Node { func (p *Parser) parseListIndex(kind ParsingContext, parseElement func(p *Parser, index int) *ast.Node) []*ast.Node { saveParsingContexts := p.parsingContexts p.parsingContexts |= 1 << kind + outerReparseList := p.reparseList + p.reparseList = nil list := make([]*ast.Node, 0, 16) for i := 0; !p.isListTerminator(kind); i++ { if p.isListElement(kind, false /*inErrorRecovery*/) { elt := parseElement(p, i) if len(p.reparseList) > 0 { - list = append(list, p.reparseList...) + for _, e := range p.reparseList { + // Propagate @typedef type alias declarations outwards to a context that permits them. + if (ast.IsJSTypeAliasDeclaration(e) || ast.IsJSImportDeclaration(e)) && kind != PCSourceElements && kind != PCBlockStatements { + outerReparseList = append(outerReparseList, e) + } else { + list = append(list, e) + } + } p.reparseList = nil } list = append(list, elt) @@ -513,6 +522,7 @@ func (p *Parser) parseListIndex(kind ParsingContext, parseElement func(p *Parser break } } + p.reparseList = outerReparseList p.parsingContexts = saveParsingContexts return p.nodeSlicePool.Clone(list) } diff --git a/testdata/baselines/reference/compiler/typedefHoisting.errors.txt b/testdata/baselines/reference/compiler/typedefHoisting.errors.txt new file mode 100644 index 0000000000..d4264baa84 --- /dev/null +++ b/testdata/baselines/reference/compiler/typedefHoisting.errors.txt @@ -0,0 +1,25 @@ +error TS5055: Cannot write file 'x.js' because it would overwrite input file. + Adding a tsconfig.json file will help organize projects that contain both TypeScript and JavaScript files. Learn more at https://aka.ms/tsconfig. +error TS5055: Cannot write file 'y.js' because it would overwrite input file. + Adding a tsconfig.json file will help organize projects that contain both TypeScript and JavaScript files. Learn more at https://aka.ms/tsconfig. + + +!!! error TS5055: Cannot write file 'x.js' because it would overwrite input file. +!!! error TS5055: Adding a tsconfig.json file will help organize projects that contain both TypeScript and JavaScript files. Learn more at https://aka.ms/tsconfig. +!!! error TS5055: Cannot write file 'y.js' because it would overwrite input file. +!!! error TS5055: Adding a tsconfig.json file will help organize projects that contain both TypeScript and JavaScript files. Learn more at https://aka.ms/tsconfig. +==== x.js (0 errors) ==== + class C { + /** @import {Bar} from "./y" */ + /** @typedef {Bar[]} Bars */ + /** @type {Bars} */ + foo = ["abc", "def"] + bar(/** @type {Bar} */ x) { + return x + } + } + +==== y.js (0 errors) ==== + /** @typedef {string} Bar */ + export {} + \ No newline at end of file diff --git a/testdata/baselines/reference/compiler/typedefHoisting.js b/testdata/baselines/reference/compiler/typedefHoisting.js new file mode 100644 index 0000000000..6803d6b512 --- /dev/null +++ b/testdata/baselines/reference/compiler/typedefHoisting.js @@ -0,0 +1,34 @@ +//// [tests/cases/compiler/typedefHoisting.ts] //// + +//// [x.js] +class C { + /** @import {Bar} from "./y" */ + /** @typedef {Bar[]} Bars */ + /** @type {Bars} */ + foo = ["abc", "def"] + bar(/** @type {Bar} */ x) { + return x + } +} + +//// [y.js] +/** @typedef {string} Bar */ +export {} + + + + +//// [y.d.ts] +export type Bar = string; +/** @typedef {string} Bar */ +export {}; +//// [x.d.ts] +import type { Bar } from "./y"; +type Bars = Bar[]; +declare class C { + /** @import {Bar} from "./y" */ + /** @typedef {Bar[]} Bars */ + /** @type {Bars} */ + foo: Bars; + bar(/** @type {Bar} */ x: Bar): string; +} diff --git a/testdata/baselines/reference/compiler/typedefHoisting.symbols b/testdata/baselines/reference/compiler/typedefHoisting.symbols new file mode 100644 index 0000000000..7202639df6 --- /dev/null +++ b/testdata/baselines/reference/compiler/typedefHoisting.symbols @@ -0,0 +1,26 @@ +//// [tests/cases/compiler/typedefHoisting.ts] //// + +=== x.js === +class C { +>C : Symbol(C, Decl(x.js, 0, 0)) + + /** @import {Bar} from "./y" */ + /** @typedef {Bar[]} Bars */ + /** @type {Bars} */ + foo = ["abc", "def"] +>foo : Symbol(C.foo, Decl(x.js, 0, 9)) + + bar(/** @type {Bar} */ x) { +>bar : Symbol(C.bar, Decl(x.js, 4, 24)) +>x : Symbol(x, Decl(x.js, 5, 8)) + + return x +>x : Symbol(x, Decl(x.js, 5, 8)) + } +} + +=== y.js === + +/** @typedef {string} Bar */ +export {} + diff --git a/testdata/baselines/reference/compiler/typedefHoisting.types b/testdata/baselines/reference/compiler/typedefHoisting.types new file mode 100644 index 0000000000..5b60cac604 --- /dev/null +++ b/testdata/baselines/reference/compiler/typedefHoisting.types @@ -0,0 +1,29 @@ +//// [tests/cases/compiler/typedefHoisting.ts] //// + +=== x.js === +class C { +>C : C + + /** @import {Bar} from "./y" */ + /** @typedef {Bar[]} Bars */ + /** @type {Bars} */ + foo = ["abc", "def"] +>foo : Bars +>["abc", "def"] : string[] +>"abc" : "abc" +>"def" : "def" + + bar(/** @type {Bar} */ x) { +>bar : (x: string) => string +>x : string + + return x +>x : string + } +} + +=== y.js === + +/** @typedef {string} Bar */ +export {} + diff --git a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.errors.txt b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.errors.txt deleted file mode 100644 index 9b0c649c61..0000000000 --- a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.errors.txt +++ /dev/null @@ -1,20 +0,0 @@ -callbackOnConstructor.js(12,12): error TS2304: Cannot find name 'ValueGetter_2'. - - -==== callbackOnConstructor.js (1 errors) ==== - export class Preferences { - assignability = "no" - /** - * @callback ValueGetter_2 - * @param {string} name - * @returns {boolean|number|string|undefined} - */ - constructor() {} - } - - - /** @type {ValueGetter_2} */ - ~~~~~~~~~~~~~ -!!! error TS2304: Cannot find name 'ValueGetter_2'. - var ooscope2 = s => s.length > 0 - \ No newline at end of file diff --git a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.js b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.js index 431cb909b3..e9feaf36f4 100644 --- a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.js +++ b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.js @@ -35,9 +35,9 @@ var ooscope2 = s => s.length > 0; //// [callbackOnConstructor.d.ts] +export type ValueGetter_2 = (name: string) => boolean | number | string | undefined; export declare class Preferences { assignability: string; - export type ValueGetter_2 = (name: string) => boolean | number | string | undefined; /** * @callback ValueGetter_2 * @param {string} name diff --git a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.js.diff b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.js.diff index 45a701f8e7..7650b96ec3 100644 --- a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.js.diff +++ b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.js.diff @@ -22,9 +22,9 @@ //// [callbackOnConstructor.d.ts] -export class Preferences { ++export type ValueGetter_2 = (name: string) => boolean | number | string | undefined; +export declare class Preferences { assignability: string; -+ export type ValueGetter_2 = (name: string) => boolean | number | string | undefined; + /** + * @callback ValueGetter_2 + * @param {string} name diff --git a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.symbols b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.symbols index 675c7c5e85..d5559f79e0 100644 --- a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.symbols +++ b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.symbols @@ -20,5 +20,7 @@ export class Preferences { var ooscope2 = s => s.length > 0 >ooscope2 : Symbol(ooscope2, Decl(callbackOnConstructor.js, 12, 3)) >s : Symbol(s, Decl(callbackOnConstructor.js, 12, 14)) +>s.length : Symbol(String.length, Decl(lib.es5.d.ts, --, --)) >s : Symbol(s, Decl(callbackOnConstructor.js, 12, 14)) +>length : Symbol(String.length, Decl(lib.es5.d.ts, --, --)) diff --git a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.symbols.diff b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.symbols.diff deleted file mode 100644 index eeddc1fb04..0000000000 --- a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.symbols.diff +++ /dev/null @@ -1,9 +0,0 @@ ---- old.callbackOnConstructor.symbols -+++ new.callbackOnConstructor.symbols -@@= skipped -19, +19 lines =@@ - var ooscope2 = s => s.length > 0 - >ooscope2 : Symbol(ooscope2, Decl(callbackOnConstructor.js, 12, 3)) - >s : Symbol(s, Decl(callbackOnConstructor.js, 12, 14)) -->s.length : Symbol(String.length, Decl(lib.es5.d.ts, --, --)) - >s : Symbol(s, Decl(callbackOnConstructor.js, 12, 14)) -->length : Symbol(String.length, Decl(lib.es5.d.ts, --, --)) diff --git a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.types b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.types index 448a21aa29..ea3a0f2df3 100644 --- a/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.types +++ b/testdata/baselines/reference/submodule/conformance/callbackOnConstructor.types @@ -20,11 +20,11 @@ export class Preferences { /** @type {ValueGetter_2} */ var ooscope2 = s => s.length > 0 >ooscope2 : ValueGetter_2 ->s => s.length > 0 : (s: any) => boolean ->s : any +>s => s.length > 0 : (s: string) => boolean +>s : string >s.length > 0 : boolean ->s.length : any ->s : any ->length : any +>s.length : number +>s : string +>length : number >0 : 0 diff --git a/testdata/baselines/reference/submodule/conformance/jsdocTemplateClass.errors.txt b/testdata/baselines/reference/submodule/conformance/jsdocTemplateClass.errors.txt index 75303c2689..02cf3bbbec 100644 --- a/testdata/baselines/reference/submodule/conformance/jsdocTemplateClass.errors.txt +++ b/testdata/baselines/reference/submodule/conformance/jsdocTemplateClass.errors.txt @@ -1,7 +1,9 @@ +templateTagOnClasses.js(7,23): error TS2304: Cannot find name 'T'. +templateTagOnClasses.js(7,29): error TS2304: Cannot find name 'T'. templateTagOnClasses.js(25,1): error TS2322: Type 'boolean' is not assignable to type 'number'. -==== templateTagOnClasses.js (1 errors) ==== +==== templateTagOnClasses.js (3 errors) ==== /** * @template T * @typedef {(t: T) => T} Id @@ -9,6 +11,10 @@ templateTagOnClasses.js(25,1): error TS2322: Type 'boolean' is not assignable to /** @template T */ class Foo { /** @typedef {(t: T) => T} Id2 */ + ~ +!!! error TS2304: Cannot find name 'T'. + ~ +!!! error TS2304: Cannot find name 'T'. /** @param {T} x */ constructor (x) { this.a = x diff --git a/testdata/baselines/reference/submodule/conformance/jsdocTemplateClass.types b/testdata/baselines/reference/submodule/conformance/jsdocTemplateClass.types index 550c90bd8a..4ba0f951be 100644 --- a/testdata/baselines/reference/submodule/conformance/jsdocTemplateClass.types +++ b/testdata/baselines/reference/submodule/conformance/jsdocTemplateClass.types @@ -29,14 +29,14 @@ class Foo { * @return {T} */ foo(x, y, alpha) { ->foo : (x: T, y: Id, alpha: (t: T) => T) => T +>foo : (x: T, y: Id, alpha: Id2) => T >x : T >y : Id ->alpha : (t: T) => T +>alpha : Id2 return alpha(y(x)) >alpha(y(x)) : T ->alpha : (t: T) => T +>alpha : Id2 >y(x) : T >y : Id >x : T diff --git a/testdata/baselines/reference/submodule/conformance/typedefInnerNamepaths.errors.txt b/testdata/baselines/reference/submodule/conformance/typedefInnerNamepaths.errors.txt index 2aa319ce1c..5a5e1fedf5 100644 --- a/testdata/baselines/reference/submodule/conformance/typedefInnerNamepaths.errors.txt +++ b/testdata/baselines/reference/submodule/conformance/typedefInnerNamepaths.errors.txt @@ -1,14 +1,20 @@ +bug25104.js(1,7): error TS2300: Duplicate identifier 'C'. bug25104.js(3,19): error TS1005: '}' expected. +bug25104.js(4,26): error TS2300: Duplicate identifier 'C'. bug25104.js(6,18): error TS1005: '}' expected. -==== bug25104.js (2 errors) ==== +==== bug25104.js (4 errors) ==== class C { + ~ +!!! error TS2300: Duplicate identifier 'C'. /** * @typedef {C~A} C~B ~ !!! error TS1005: '}' expected. * @typedef {object} C~A + ~ +!!! error TS2300: Duplicate identifier 'C'. */ /** @param {C~A} o */ ~ diff --git a/testdata/baselines/reference/submodule/conformance/typedefOnSemicolonClassElement.js b/testdata/baselines/reference/submodule/conformance/typedefOnSemicolonClassElement.js index 230abbb8ef..bae46ccae5 100644 --- a/testdata/baselines/reference/submodule/conformance/typedefOnSemicolonClassElement.js +++ b/testdata/baselines/reference/submodule/conformance/typedefOnSemicolonClassElement.js @@ -23,31 +23,8 @@ exports.Preferences = Preferences; //// [typedefOnSemicolonClassElement.d.ts] +export type A = string; export declare class Preferences { - type A = string; /** @type {A} */ a: A; } - - -//// [DtsFileErrors] - - -dist/typedefOnSemicolonClassElement.d.ts(2,5): error TS1068: Unexpected token. A constructor, method, accessor, or property was expected. -dist/typedefOnSemicolonClassElement.d.ts(4,8): error TS2693: 'A' only refers to a type, but is being used as a value here. -dist/typedefOnSemicolonClassElement.d.ts(5,1): error TS1128: Declaration or statement expected. - - -==== dist/typedefOnSemicolonClassElement.d.ts (3 errors) ==== - export declare class Preferences { - type A = string; - ~~~~ -!!! error TS1068: Unexpected token. A constructor, method, accessor, or property was expected. - /** @type {A} */ - a: A; - ~ -!!! error TS2693: 'A' only refers to a type, but is being used as a value here. - } - ~ -!!! error TS1128: Declaration or statement expected. - \ No newline at end of file diff --git a/testdata/baselines/reference/submodule/conformance/typedefOnSemicolonClassElement.js.diff b/testdata/baselines/reference/submodule/conformance/typedefOnSemicolonClassElement.js.diff index d4a2b25707..d4bf30386b 100644 --- a/testdata/baselines/reference/submodule/conformance/typedefOnSemicolonClassElement.js.diff +++ b/testdata/baselines/reference/submodule/conformance/typedefOnSemicolonClassElement.js.diff @@ -18,32 +18,9 @@ //// [typedefOnSemicolonClassElement.d.ts] -export class Preferences { ++export type A = string; +export declare class Preferences { -+ type A = string; /** @type {A} */ - a: string; + a: A; - } -+ -+ -+//// [DtsFileErrors] -+ -+ -+dist/typedefOnSemicolonClassElement.d.ts(2,5): error TS1068: Unexpected token. A constructor, method, accessor, or property was expected. -+dist/typedefOnSemicolonClassElement.d.ts(4,8): error TS2693: 'A' only refers to a type, but is being used as a value here. -+dist/typedefOnSemicolonClassElement.d.ts(5,1): error TS1128: Declaration or statement expected. -+ -+ -+==== dist/typedefOnSemicolonClassElement.d.ts (3 errors) ==== -+ export declare class Preferences { -+ type A = string; -+ ~~~~ -+!!! error TS1068: Unexpected token. A constructor, method, accessor, or property was expected. -+ /** @type {A} */ -+ a: A; -+ ~ -+!!! error TS2693: 'A' only refers to a type, but is being used as a value here. -+ } -+ ~ -+!!! error TS1128: Declaration or statement expected. -+ \ No newline at end of file + } \ No newline at end of file diff --git a/testdata/baselines/reference/submoduleAccepted/conformance/callbackOnConstructor.errors.txt.diff b/testdata/baselines/reference/submoduleAccepted/conformance/callbackOnConstructor.errors.txt.diff deleted file mode 100644 index e019fdce7f..0000000000 --- a/testdata/baselines/reference/submoduleAccepted/conformance/callbackOnConstructor.errors.txt.diff +++ /dev/null @@ -1,24 +0,0 @@ ---- old.callbackOnConstructor.errors.txt -+++ new.callbackOnConstructor.errors.txt -@@= skipped -0, +0 lines =@@ -- -+callbackOnConstructor.js(12,12): error TS2304: Cannot find name 'ValueGetter_2'. -+ -+ -+==== callbackOnConstructor.js (1 errors) ==== -+ export class Preferences { -+ assignability = "no" -+ /** -+ * @callback ValueGetter_2 -+ * @param {string} name -+ * @returns {boolean|number|string|undefined} -+ */ -+ constructor() {} -+ } -+ -+ -+ /** @type {ValueGetter_2} */ -+ ~~~~~~~~~~~~~ -+!!! error TS2304: Cannot find name 'ValueGetter_2'. -+ var ooscope2 = s => s.length > 0 -+ \ No newline at end of file diff --git a/testdata/baselines/reference/submoduleAccepted/conformance/callbackOnConstructor.types.diff b/testdata/baselines/reference/submoduleAccepted/conformance/callbackOnConstructor.types.diff index 1f736624c7..2869da9615 100644 --- a/testdata/baselines/reference/submoduleAccepted/conformance/callbackOnConstructor.types.diff +++ b/testdata/baselines/reference/submoduleAccepted/conformance/callbackOnConstructor.types.diff @@ -6,15 +6,8 @@ var ooscope2 = s => s.length > 0 ->ooscope2 : (name: string) => boolean | number | string | undefined ->s => s.length > 0 : (s: string) => string | number | boolean -->s : string +>ooscope2 : ValueGetter_2 -+>s => s.length > 0 : (s: any) => boolean -+>s : any ++>s => s.length > 0 : (s: string) => boolean + >s : string >s.length > 0 : boolean -->s.length : number -->s : string -->length : number -+>s.length : any -+>s : any -+>length : any - >0 : 0 + >s.length : number \ No newline at end of file diff --git a/testdata/baselines/reference/submoduleAccepted/conformance/jsdocTemplateClass.errors.txt.diff b/testdata/baselines/reference/submoduleAccepted/conformance/jsdocTemplateClass.errors.txt.diff new file mode 100644 index 0000000000..7aafc7f02d --- /dev/null +++ b/testdata/baselines/reference/submoduleAccepted/conformance/jsdocTemplateClass.errors.txt.diff @@ -0,0 +1,24 @@ +--- old.jsdocTemplateClass.errors.txt ++++ new.jsdocTemplateClass.errors.txt +@@= skipped -0, +0 lines =@@ ++templateTagOnClasses.js(7,23): error TS2304: Cannot find name 'T'. ++templateTagOnClasses.js(7,29): error TS2304: Cannot find name 'T'. + templateTagOnClasses.js(25,1): error TS2322: Type 'boolean' is not assignable to type 'number'. + + +-==== templateTagOnClasses.js (1 errors) ==== ++==== templateTagOnClasses.js (3 errors) ==== + /** + * @template T + * @typedef {(t: T) => T} Id +@@= skipped -8, +10 lines =@@ + /** @template T */ + class Foo { + /** @typedef {(t: T) => T} Id2 */ ++ ~ ++!!! error TS2304: Cannot find name 'T'. ++ ~ ++!!! error TS2304: Cannot find name 'T'. + /** @param {T} x */ + constructor (x) { + this.a = x \ No newline at end of file diff --git a/testdata/baselines/reference/submoduleAccepted/conformance/jsdocTemplateClass.types.diff b/testdata/baselines/reference/submoduleAccepted/conformance/jsdocTemplateClass.types.diff new file mode 100644 index 0000000000..46539f9422 --- /dev/null +++ b/testdata/baselines/reference/submoduleAccepted/conformance/jsdocTemplateClass.types.diff @@ -0,0 +1,20 @@ +--- old.jsdocTemplateClass.types ++++ new.jsdocTemplateClass.types +@@= skipped -28, +28 lines =@@ + * @return {T} + */ + foo(x, y, alpha) { +->foo : (x: T, y: Id, alpha: (t: T) => T) => T ++>foo : (x: T, y: Id, alpha: Id2) => T + >x : T + >y : Id +->alpha : (t: T) => T ++>alpha : Id2 + + return alpha(y(x)) + >alpha(y(x)) : T +->alpha : (t: T) => T ++>alpha : Id2 + >y(x) : T + >y : Id + >x : T \ No newline at end of file diff --git a/testdata/baselines/reference/submoduleAccepted/conformance/typedefInnerNamepaths.errors.txt.diff b/testdata/baselines/reference/submoduleAccepted/conformance/typedefInnerNamepaths.errors.txt.diff index 668a3e4dd1..db8d8129a0 100644 --- a/testdata/baselines/reference/submoduleAccepted/conformance/typedefInnerNamepaths.errors.txt.diff +++ b/testdata/baselines/reference/submoduleAccepted/conformance/typedefInnerNamepaths.errors.txt.diff @@ -1,25 +1,20 @@ --- old.typedefInnerNamepaths.errors.txt +++ new.typedefInnerNamepaths.errors.txt @@= skipped -0, +0 lines =@@ --bug25104.js(1,7): error TS2300: Duplicate identifier 'C'. + bug25104.js(1,7): error TS2300: Duplicate identifier 'C'. bug25104.js(3,19): error TS1005: '}' expected. --bug25104.js(4,26): error TS2300: Duplicate identifier 'C'. + bug25104.js(4,26): error TS2300: Duplicate identifier 'C'. -bug25104.js(6,18): error TS8024: JSDoc '@param' tag has name '', but there is no parameter with that name. bug25104.js(6,18): error TS1005: '}' expected. -==== bug25104.js (5 errors) ==== -+==== bug25104.js (2 errors) ==== ++==== bug25104.js (4 errors) ==== class C { -- ~ --!!! error TS2300: Duplicate identifier 'C'. - /** - * @typedef {C~A} C~B - ~ - !!! error TS1005: '}' expected. - * @typedef {object} C~A -- ~ --!!! error TS2300: Duplicate identifier 'C'. + ~ + !!! error TS2300: Duplicate identifier 'C'. +@@= skipped -17, +16 lines =@@ + !!! error TS2300: Duplicate identifier 'C'. */ /** @param {C~A} o */ - diff --git a/testdata/tests/cases/compiler/typedefHoisting.ts b/testdata/tests/cases/compiler/typedefHoisting.ts new file mode 100644 index 0000000000..80683421ee --- /dev/null +++ b/testdata/tests/cases/compiler/typedefHoisting.ts @@ -0,0 +1,18 @@ +// @allowJs: true +// @checkJs: true +// @declaration: true + +// @filename: x.js +class C { + /** @import {Bar} from "./y" */ + /** @typedef {Bar[]} Bars */ + /** @type {Bars} */ + foo = ["abc", "def"] + bar(/** @type {Bar} */ x) { + return x + } +} + +// @filename: y.js +/** @typedef {string} Bar */ +export {}