Skip to content

Commit c8f2405

Browse files
authored
Fixed an issue with top-level for-await loops not being allowed with --module preserve (#59042)
1 parent 15f67e0 commit c8f2405

7 files changed

+94
-0
lines changed

src/compiler/checker.ts

+1
Original file line numberDiff line numberDiff line change
@@ -51097,6 +51097,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
5109751097
// fallthrough
5109851098
case ModuleKind.ES2022:
5109951099
case ModuleKind.ESNext:
51100+
case ModuleKind.Preserve:
5110051101
case ModuleKind.System:
5110151102
if (languageVersion >= ScriptTarget.ES2017) {
5110251103
break;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
modulePreserveTopLevelAwait1.ts(1,5): error TS1432: Top-level 'for await' loops are only allowed when the 'module' option is set to 'es2022', 'esnext', 'system', 'node16', 'nodenext', or 'preserve', and the 'target' option is set to 'es2017' or higher.
2+
modulePreserveTopLevelAwait1.ts(2,1): error TS1378: Top-level 'await' expressions are only allowed when the 'module' option is set to 'es2022', 'esnext', 'system', 'node16', 'nodenext', or 'preserve', and the 'target' option is set to 'es2017' or higher.
3+
4+
5+
==== modulePreserveTopLevelAwait1.ts (2 errors) ====
6+
for await (const x of []) {}
7+
~~~~~
8+
!!! error TS1432: Top-level 'for await' loops are only allowed when the 'module' option is set to 'es2022', 'esnext', 'system', 'node16', 'nodenext', or 'preserve', and the 'target' option is set to 'es2017' or higher.
9+
await Promise.resolve();
10+
~~~~~
11+
!!! error TS1378: Top-level 'await' expressions are only allowed when the 'module' option is set to 'es2022', 'esnext', 'system', 'node16', 'nodenext', or 'preserve', and the 'target' option is set to 'es2017' or higher.
12+
13+
export {};
14+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
//// [tests/cases/compiler/modulePreserveTopLevelAwait1.ts] ////
2+
3+
=== modulePreserveTopLevelAwait1.ts ===
4+
for await (const x of []) {}
5+
>x : Symbol(x, Decl(modulePreserveTopLevelAwait1.ts, 0, 16))
6+
7+
await Promise.resolve();
8+
>Promise.resolve : Symbol(PromiseConstructor.resolve, Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --))
9+
>Promise : Symbol(Promise, Decl(lib.es5.d.ts, --, --), Decl(lib.es2015.iterable.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.symbol.wellknown.d.ts, --, --))
10+
>resolve : Symbol(PromiseConstructor.resolve, Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --))
11+
12+
export {};
13+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
//// [tests/cases/compiler/modulePreserveTopLevelAwait1.ts] ////
2+
3+
=== modulePreserveTopLevelAwait1.ts ===
4+
for await (const x of []) {}
5+
>x : any
6+
> : ^^^
7+
>[] : undefined[]
8+
> : ^^^^^^^^^^^
9+
10+
await Promise.resolve();
11+
>await Promise.resolve() : void
12+
> : ^^^^
13+
>Promise.resolve() : Promise<void>
14+
> : ^^^^^^^^^^^^^
15+
>Promise.resolve : { (): Promise<void>; <T>(value: T): Promise<Awaited<T>>; <T>(value: T | PromiseLike<T>): Promise<Awaited<T>>; }
16+
> : ^^^^^^ ^^^ ^^ ^^ ^^^ ^^^ ^^ ^^ ^^^ ^^^
17+
>Promise : PromiseConstructor
18+
> : ^^^^^^^^^^^^^^^^^^
19+
>resolve : { (): Promise<void>; <T>(value: T): Promise<Awaited<T>>; <T>(value: T | PromiseLike<T>): Promise<Awaited<T>>; }
20+
> : ^^^^^^ ^^^ ^^ ^^ ^^^ ^^^ ^^ ^^ ^^^ ^^^
21+
22+
export {};
23+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
//// [tests/cases/compiler/modulePreserveTopLevelAwait1.ts] ////
2+
3+
=== modulePreserveTopLevelAwait1.ts ===
4+
for await (const x of []) {}
5+
>x : Symbol(x, Decl(modulePreserveTopLevelAwait1.ts, 0, 16))
6+
7+
await Promise.resolve();
8+
>Promise.resolve : Symbol(PromiseConstructor.resolve, Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --))
9+
>Promise : Symbol(Promise, Decl(lib.es5.d.ts, --, --), Decl(lib.es2015.iterable.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.symbol.wellknown.d.ts, --, --), Decl(lib.es2018.promise.d.ts, --, --))
10+
>resolve : Symbol(PromiseConstructor.resolve, Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --))
11+
12+
export {};
13+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
//// [tests/cases/compiler/modulePreserveTopLevelAwait1.ts] ////
2+
3+
=== modulePreserveTopLevelAwait1.ts ===
4+
for await (const x of []) {}
5+
>x : any
6+
>[] : undefined[]
7+
> : ^^^^^^^^^^^
8+
9+
await Promise.resolve();
10+
>await Promise.resolve() : void
11+
> : ^^^^
12+
>Promise.resolve() : Promise<void>
13+
> : ^^^^^^^^^^^^^
14+
>Promise.resolve : { (): Promise<void>; <T>(value: T): Promise<Awaited<T>>; <T>(value: T | PromiseLike<T>): Promise<Awaited<T>>; }
15+
> : ^^^^^^ ^^^ ^^ ^^ ^^^ ^^^ ^^ ^^ ^^^ ^^^
16+
>Promise : PromiseConstructor
17+
> : ^^^^^^^^^^^^^^^^^^
18+
>resolve : { (): Promise<void>; <T>(value: T): Promise<Awaited<T>>; <T>(value: T | PromiseLike<T>): Promise<Awaited<T>>; }
19+
> : ^^^^^^ ^^^ ^^ ^^ ^^^ ^^^ ^^ ^^ ^^^ ^^^
20+
21+
export {};
22+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
// @module: preserve
2+
// @target: es2016, esnext
3+
// @noEmit: true
4+
5+
for await (const x of []) {}
6+
await Promise.resolve();
7+
8+
export {};

0 commit comments

Comments
 (0)